MATLAB eig有时会返回反向符号 [英] MATLAB eig returns inverted signs sometimes

查看:130
本文介绍了MATLAB eig有时会返回反向符号的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我正在尝试编写一个程序,该程序可以获取任意大小的矩阵A,然后SVD对其进行分解:

I'm trying to write a program that gets a matrix A of any size, and SVD decomposes it:

A = U * S * V'

其中A是用户输入的矩阵,U是由A * A'的特征向量组成的正交矩阵,S是具有奇异值的对角矩阵,并且V是正交矩阵A' * A的特征向量.

Where A is the matrix the user enters, U is an orthogonal matrix composes of the eigenvectors of A * A', S is a diagonal matrix of the singular values, and V is an orthogonal matrix of the eigenvectors of A' * A.

问题是:MATLAB函数eig有时会返回错误的特征向量.

Problem is: the MATLAB function eig sometimes returns the wrong eigenvectors.

这是我的代码:

function [U,S,V]=badsvd(A)
W=A*A';
[U,S]=eig(W);
max=0;
for i=1:size(W,1) %%sort
    for j=i:size(W,1)
        if(S(j,j)>max)
            max=S(j,j);
            temp_index=j;
        end
    end
    max=0;
    temp=S(temp_index,temp_index);
    S(temp_index,temp_index)=S(i,i);
    S(i,i)=temp;
    temp=U(:,temp_index);
    U(:,temp_index)=U(:,i);
    U(:,i)=temp;
end
W=A'*A;
[V,s]=eig(W);
max=0;
for i=1:size(W,1) %%sort
    for j=i:size(W,1)
        if(s(j,j)>max)
            max=s(j,j);
            temp_index=j;
        end
    end
    max=0;
    temp=s(temp_index,temp_index);
    s(temp_index,temp_index)=s(i,i);
    s(i,i)=temp;
    temp=V(:,temp_index);
    V(:,temp_index)=V(:,i);
    V(:,i)=temp;
end
s=sqrt(s);
end

我的代码返回正确的s矩阵,并且几乎"返回正确的UV矩阵.但是某些列乘以-1.显然,如果t是一个特征向量,那么-t也是一个特征向量,但是在符号反转的情况下(对于某些列,不是全部),我不会得到A = U * S * V'.

My code returns the correct s matrix, and also "nearly" correct U and V matrices. But some of the columns are multiplied by -1. obviously if t is an eigenvector, then also -t is an eigenvector, but with the signs inverted (for some of the columns, not all) I don't get A = U * S * V'.

有什么办法可以解决这个问题?

Is there any way to fix this?

示例:对于矩阵A=[1,2;3,4],我的函数返回:

Example: for the matrix A=[1,2;3,4] my function returns:

U=[0.4046,-0.9145;0.9145,0.4046]

和内置的MATLAB svd函数返回:

and the built-in MATLAB svd function returns:

u=[-0.4046,-0.9145;-0.9145,0.4046]

推荐答案

请注意,特征向量不是唯一的.乘以任何常量,包括-1(仅更改符号),即可得出另一个有效的特征向量.鉴于特征向量的定义,这很明显:

Note that eigenvectors are not unique. Multiplying by any constant, including -1 (which simply changes the sign), gives another valid eigenvector. This is clear given the definition of an eigenvector:

A·v = λ·v

MATLAB 选择将特征向量标准化为范数为1.0的符号是任意的:

MATLAB chooses to normalize the eigenvectors to have a norm of 1.0, the sign is arbitrary:

对于eig(A),对特征向量进行缩放,以使每个向量的范数为1.0. 对于eig(A,B)eig(A,'nobalance')eig(A,B,flag),特征向量未归一化

For eig(A), the eigenvectors are scaled so that the norm of each is 1.0. For eig(A,B), eig(A,'nobalance'), and eig(A,B,flag), the eigenvectors are not normalized

现在您知道,SVD和特征分解是相关.下面是一些测试此事实的代码.请注意,svdeig返回结果的顺序不同(一个从高到低排序,另一个反向):

Now as you know, SVD and eigendecomposition are related. Below is some code to test this fact. Note that svd and eig return results in different order (one sorted high to low, the other in reverse):

% some random matrix
A = rand(5);

% singular value decomposition
[U,S,V] = svd(A);

% eigenvectors of A'*A are the same as the right-singular vectors
[V2,D2] = eig(A'*A);
[D2,ord] = sort(diag(D2), 'descend');
S2 = diag(sqrt(D2));
V2 = V2(:,ord);

% eigenvectors of A*A' are the same as the left-singular vectors
[U2,D2] = eig(A*A');
[D2,ord] = sort(diag(D2), 'descend');
S3 = diag(sqrt(D2));
U2 = U2(:,ord);

% check results
A
U*S*V'
U2*S2*V2'

我得到非常相似的结果(忽略较小的浮点错误):

I get very similar results (ignoring minor floating-point errors):

>> norm(A - U*S*V')
ans =
   7.5771e-16
>> norm(A - U2*S2*V2')
ans =
   3.2841e-14


为了获得一致的结果,通常采用一种约定,即要求每个特征向量中的第一个元素具有特定符号.这样,如果您得到的特征向量不遵循此规则,则将其乘以-1即可翻转符号...


To get consistent results, one usually adopts a convention of requiring that the first element in each eigenvector be of a certain sign. That way if you get an eigenvector that does not follow this rule, you multiply it by -1 to flip the sign...

这篇关于MATLAB eig有时会返回反向符号的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆