Неправильное вычисление собственного вектора Numpy

Я использую numpy для получения собственных значений/собственных векторов матрицы. Моя матрица симметрична и положительна.

> mat

  matrix([[ 1.,  1.,  0.,  0.,  0.,  0.,  0.],
          [ 1.,  2.,  0.,  0.,  0.,  0.,  0.],
          [ 0.,  0.,  1.,  0.,  0.,  0.,  0.],
          [ 0.,  0.,  0.,  2.,  1.,  1.,  0.],
          [ 0.,  0.,  0.,  1.,  2.,  1.,  0.],
          [ 0.,  0.,  0.,  1.,  1.,  1.,  0.],
          [ 0.,  0.,  0.,  0.,  0.,  0.,  1.]])

Я использую np.eigh, потому что моя матрица симметрична.

> import numpy.linalg as la
> la.eigh(mat)

  (array([ 0.27,  0.38,  1.  ,  1.  ,  1.  ,  2.62,  3.73]),
   matrix([[ 0.  , -0.85, -0.  ,  0.  ,  0.  ,  0.53,  0.  ],
          [ 0.  ,  0.53, -0.  ,  0.  ,  0.  ,  0.85,  0.  ],
          [ 0.  ,  0.  , -0.  ,  1.  ,  0.  ,  0.  ,  0.  ],
          [-0.33, -0.  , -0.71, -0.  , -0.  , -0.  , -0.63],
          [-0.33, -0.  ,  0.71, -0.  , -0.  , -0.  , -0.63],
          [ 0.89, -0.  , -0.  , -0.  , -0.  , -0.  , -0.46],
          [-0.  , -0.  , -0.  , -0.  ,  1.  , -0.  , -0.  ]]))

Моя проблема в том, что многие из этих значений имеют неправильный знак. В частности, главный собственный вектор (крайний правый столбец в матрице) полностью отрицателен, хотя должен быть положительным. Я проверил это как на Matlab, так и на Octave. Это просто ошибка точности, или я что-то упускаю?

Если это ошибка, есть ли способ проверить такую ​​​​ошибку и исправить ее?

EDIT: этот расчет является частью Hubs and Authorities, а приведенная выше матрица - A*A^T. Это результат исходной статьи (см. стр. 9, стр. 10), что оценки хаба сходятся к главному собственному вектору A*A^T. В конечном счете, мы хотим сравнить эти оценки узлов друг с другом, поэтому знак действительно важен.

На странице 10 в документе также говорится: «Кроме того (как следствие), если M имеет только неотрицательные элементы, то главный собственный вектор M имеет только неотрицательные элементы». Вот почему я задал вопрос.


person mayhewsw    schedule 12.02.2014    source источник
comment
Результаты правильные. Знак собственного вектора не определен и является произвольным.   -  person pv.    schedule 13.02.2014
comment
Ни одна из этих ссылок не противоречит тому факту, что знак собственного вектора не определен. Конечно, вы можете исправить соглашение о фазах, если этого требует ваша задача, но обычно этого не делают (поскольку задачи различаются).   -  person pv.    schedule 13.02.2014


Ответы (2)


Знак собственного вектора произвольный. Насколько я знаю, в этом отношении нет правильного или неправильного ответа.

person Mike Graham    schedule 12.02.2014
comment
Спасибо, Майк. Меня действительно волнует знак собственных векторов - я отредактировал свой исходный вопрос. - person mayhewsw; 13.02.2014
comment
Похоже автор лукавил. Он должен был сказать: Кроме того (как следствие), если M имеет только неотрицательные элементы, то существует главный собственный вектор M, который имеет только неотрицательные элементы . (или что-то более ясное), что на самом деле говорит теорема Перрона-Фробениуса. - person Mike Graham; 13.02.2014
comment
Чтобы получить нужный вам знак, смело переворачивайте знак на весь вектор. - person Mike Graham; 13.02.2014
comment
Да, я тоже рассматривал теорему Перрона-Фробениуса. Понятно, что итерационный метод, описанный в статье, дает только неотрицательные результаты, но в общем случае неверен. Теперь мой вопрос: могу ли я быть уверен, что все элементы главного собственного вектора имеют одинаковый знак? Это больше математика, чем numpy. - person mayhewsw; 13.02.2014
comment
Что-то вроде eigvals, eigvecs = la.eigh(mat) principal = eigvecs[:, eigvals.argmax()] if (principal >= 0).all() or (pricipal <= 0).all(): print 'all the same'? (Не выполнялось/не тестировалось/и т. д. Кроме того, могут возникнуть числовые проблемы, когда -0.000000000218 следует считать за 0). Наверное, проще сначала написать mat.) - person Mike Graham; 13.02.2014

Вы можете легко проверить правильность собственного разложения вашей симметричной матрицы MM, если вы воспользуетесь MM == QQ*DD*QQ.T, где DD=diag([lam_1, lam2_,...]) будет матрицей с собственными значениями на диагонали, а QQ будет матрицей собственных векторов:

lam,QQ = la.eigh(MM)

# Check result:
DD = np.diag(lam)
MM2 = np.dot(np.dot(QQ, DD), QQ.T)
print(MM-MM2)  # should be zero

что в вашем случае правильно до 14 цифр.

Обратите внимание, что собственные векторы могут быть умножены на любую константу из-за определяющего уравнения собственных значений MM*x == lambda*x ‹=> MM*(c*x) == lambda *(c*x), где c является любой ненулевой константой. c зависит от числовых значений — Numpy просто нормализовал вектор до единицы.

person Dietrich    schedule 12.02.2014