2013-07-08 20 views
5

2 biçimine döndürür. this question içinde, belirli bir matrisin lower ve upper triagular bölümlerine nasıl erişileceği açıklanır.bir simetrik matrisin üst/alt üçgen parçasını (2B dizi) 1D dizisine dönüştürür ve

indices = np.triu_indices_from(m) 
a = np.asarray(m[indices])[-1] 
#array([11, 12, 13, 22, 23, 33]) 

değerlerini değiştirerek, a hesaplama yapıyoruz sonra, kullanılacak:

m = np.matrix([[11, 12, 13], 
       [21, 22, 23], 
       [31, 32, 33]]) 

Burada yapıyor yapılabilir bir 1D dizisinde matrisi dönüştürmek gerekiyor doldurmak mmetric 2D array:

new = np.zeros(m.shape) 
for i,j in enumerate(zip(*indices)): 
    new[j]=a[i] 
    new[j[1],j[0]]=a[i] 

dönersek:

array([[ 11., 12., 13.], 
     [ 12., 22., 23.], 
     [ 13., 23., 33.]]) 

Bunu gerçekleştirmek için daha iyi bir yolu var mı? Daha özel olarak, 2D dizisini yeniden oluşturmak için Python döngüsünden kaçınmak mı istiyorsunuz?

cevap

5

Simetrik bir dizi oluşturmak mı istiyorsunuz? Çapraz indeksleri tamamen atlayabilirsiniz.

>>> m=np.array(m) 
>>> inds = np.triu_indices_from(m,k=1) 
>>> m[(inds[1], inds[0])] = m[inds] 
>>> m 
array([[11, 12, 13], 
     [12, 22, 23], 
     [13, 23, 33]]) 

bir bir simetrik dizi oluşturma:

>>> new = np.zeros((3,3)) 
>>> vals = np.array([11, 12, 13, 22, 23, 33]) 
>>> inds = np.triu_indices_from(new) 
>>> new[inds] = vals 
>>> new[(inds[1], inds[0])] = vals 
>>> new 
array([[ 11., 12., 13.], 
     [ 12., 22., 23.], 
     [ 13., 23., 33.]]) 
+0

Ben simetrik '2D-array' dönmeden önce orta vadeli dizisi' a' işlemek zorunda –

+0

Sen işleyebilirsiniz 'm Doğru sırayla 1D numpy dizisi döndürdüğü sürece. Bununla ilgili özel bir sorun mu var? – Daniel

+0

a dizisinden ([11, 12, 13, 22, 23, 33]) 'dan karşılık gelen bir 2B dizi dizisine ([[11,12,13], [12,22,23], [13,23,33]]) ' –

3

Böyle numpy.triu, numpy.tril ve numpy.diag gibi bir üçgen bir simetrik bir matris oluşturmak için Array Creation Routines kullanabilir. İşte basit bir 3x3 örneği.

a = np.array([[1,2,3],[4,5,6],[7,8,9]]) 
array([[1, 2, 3], 
     [4, 5, 6], 
     [7, 8, 9]]) 

a_triu = np.triu(a, k=0) 
array([[1, 2, 3], 
     [0, 5, 6], 
     [0, 0, 9]]) 

a_tril = np.tril(a, k=0) 
array([[1, 0, 0], 
     [4, 5, 0], 
     [7, 8, 9]]) 

a_diag = np.diag(np.diag(a)) 
array([[1, 0, 0], 
     [0, 5, 0], 
     [0, 0, 9]]) 

devrik ekleyin ve diyagonal çıkarma: [indup

a_sym_triu = a_triu + a_triu.T - a_diag 
array([[1, 2, 3], 
     [2, 5, 6], 
     [3, 6, 9]]) 

a_sym_tril = a_tril + a_tril.T - a_diag 
array([[1, 4, 7], 
     [4, 5, 8], 
     [7, 8, 9]]) 
+0

teşekkürler;) –

+0

I a' 'dizisi ([[22., 12., 13.], [12, 44, 23], olduğu ortaya çıkıyor' aynı adımları gerçekleştirilebilir ancak [13., 23., 66.]]) ' – Madhav

+1

@Madhav'a kendiliğinden köşegen elemanlar eklenir, bu ileti k = 0 olduğunda köşegenleri içerdiğinden, numpy np.tril ve np.triu bilgilerini güncellemiş olabilir. Ya da orijinal yanıtım yanlış olmuş olabilir. Np.diag ile köşegeni çıkararak düzelttim. –