cv :: eigen создает транспонированные собственные векторы w.r.t. те из Matlab

Я написал C ++ версию этот Функция Matlab для вычисления PCA (обратите внимание, что здесь данные по столбцам, как в исходном коде Matlab). Если вы заинтересованы:

  • U полученная матрица вращения
  • lams являются собственными значениями x
  • Utmu это просто U.t()*mu
  • x это матрица данных
  • nPCs количество основных компонентов, которые мы хотим сохранить

Это мой код на C ++ (не стесняйтесь его просматривать):

template <typename T>
void cc::relja_PCA(T &U, T &lams, T &mu, T &Utmu, const T &x, size_t nPCs, const bool substractMean){
int nPoints = x.cols;
int nDims = x.rows;

if(nPCs <= 0)
nPCs = nDims;

if(substractMean){
cv::reduce(x,mu, 1, CV_REDUCE_AVG);
for(int i=0; i<nPoints; i++){
x.col(i) = x.col(i) - mu;
}
}
else
mu = cv::Mat::zeros(1, nDims, x.type());

bool doDual;
T X2;
if(nDims<=nPoints){
doDual = false;
cv::mulTransposed(x,X2, false);
}
else{
doDual = true;
cv::mulTransposed(x, X2, true);
}

X2 /= (nPoints-1);

cv::eigen(X2, lams, U);

U = U.t();//save only the first nPCs elements of L, which is already a vector
if(nPCs>0 && nPCs<X2.rows){
lams(cv::Range(0, nPCs), cv::Range(0, lams.cols)).copyTo(lams);
U(cv::Range(0,U.rows),cv::Range(0,nPCs)).copyTo(U);
}

if (doDual){

cv::Mat1f diag = lams.clone();
for(int i=0; i<diag.rows; i++)
diag.at<float>(i,1) = diag.at<float>(i,1) > 1e-9 ? diag.at<float>(i,1) : 1e-9;
cv::sqrt(diag, diag);
diag = 1.0f/diag;
diag = cv::Mat::diag(diag);
U = x * (U * diag / std::sqrt(nPoints-1)) ;
}

Utmu = U.t() * mu;

}

Функция вызывается с помощью:

//given some nPCs
cv::Mat1f U, lams, mu, Utmu;
cc::relja_PCA(U, lams, mu, Utmu, mat, nPCs);

И проекция вектора причудливого столбца feat сделано с:

feat = U.t()*feat - Utmu; //or equivalently feat = U.t() * (feat- mu);

У меня есть 2 вопроса:

  1. Зачем U в cv::eigen(X2, lams, U); это транспонированная версия [U, L]= eigs(X2, nPCs); ? Как видите, чтобы гарантировать те же результаты исходного кода, я должен U=U.t();, Зачем? Я заметил это во время тестирования кода с игрушечной матрицей 5×4 и nPCs = 3.
  2. Мы знаем что знак собственных векторов не имеет значения, но мне интересно, может ли это создать какие-либо проблемы в этом контексте. Я заметил это некоторые из столбцов U был напротив w.r.t. те из Matlab.

0

Решение

Задача ещё не решена.

Другие решения

Других решений пока нет …

По вопросам рекламы ammmcru@yandex.ru
Adblock
detector