Eigenvalue Decomposition Issue in Python Numpy

681 Views Asked by At

I am having some issues with Python's Numpy.linalg package.

Eigenvalue decomposition:
Given X, find the eigen values (e_val) and the eigen vectors (e_vector), such that:

X * e_val = e_val * e_vector

I am using np.linalg.eigh, the documentation says it works for real symmetric matrixes.

Part 1: An example where numpy.linalg works fine (left-hand side equals right-hand side)

Code:

X = [[ 0.625, -0.125],
     [-0.125, -0.125]]
e_vals, e_vectors = np.linalg.eigh(X)
print('eigen values: \n', e_vals)
print('eigen vectors:\n', e_vectors)
print('...')
print('left: ', np.dot(X, e_vectors[0]))
print('right:', np.dot(e_vals[0], e_vectors[0]))
print('...')
print('left: ', np.dot(X, e_vectors[1]))
print('right:', np.dot(e_vals[1], e_vectors[1]))

Output:

eigen values: 
 [-0.14528471  0.64528471]
eigen vectors:
 [[-0.16018224 -0.98708746]
 [-0.98708746  0.16018224]]
...
left:  [0.02327203 0.14340871]
right: [0.02327203 0.14340871]
...
left:  [-0.63695244  0.10336315]
right: [-0.63695244  0.10336315]

Part 2: An example where numpy.linalg doesn't works (left-hand side not equals right-hand side)

Code:

X = [[-0.125, -0.375],
     [-0.375, -0.375]]
e_vals, e_vectors = np.linalg.eigh(X)
print('eigen values: \n', e_vals)
print('eigen vectors:\n', e_vectors)
print('...')
print('left: ', np.dot(X, e_vectors[0]))
print('right:', np.dot(e_vals[0], e_vectors[0]))
print('...')
print('left: ', np.dot(X, e_vectors[1]))
print('right:', np.dot(e_vals[1], e_vectors[1]))

Output:

eigen values: 
 [-0.64528471  0.14528471]
eigen vectors:
 [[ 0.58471028 -0.81124219]
 [ 0.81124219  0.58471028]]
...
left:  [0.23112703 0.08494946]
right: [-0.37730461  0.52348218]
...
left:  [-0.32067163 -0.52348218]
right: [0.11786108 0.08494946]

The whole code is on My GitHub

So for some matrix X works, but for others doesn't.

Why? Can anyone please help? Thanks!

1

There are 1 best solutions below

1
On

The eigenvectors are the columns of e_vectors but you are selecting the rows instead. Replacing e_vectors[0] with e_vectors[:, 0] will fix your problem. This was not a problem in your first example because your matrix of eigenvectors was symmetric by coincidence.

X = [[-0.125, -0.375],
     [-0.375, -0.375]]
e_vals, e_vectors = np.linalg.eigh(X)
print('eigen values: \n', e_vals)
print('eigen vectors:\n', e_vectors)
print('...')
print('left: ', np.dot(X, e_vectors[:, 0]))
print('right:', np.dot(e_vals[0], e_vectors[:, 0]))
print('...')
print('left: ', np.dot(X, e_vectors[:, 1]))
print('right:', np.dot(e_vals[1], e_vectors[:, 1]))
eigen values: 
 [-0.64528471  0.14528471]
eigen vectors:
 [[ 0.58471028 -0.81124219]
 [ 0.81124219  0.58471028]]
...
left:  [-0.37730461 -0.52348218]
right: [-0.37730461 -0.52348218]
...
left:  [-0.11786108  0.08494946]
right: [-0.11786108  0.08494946]