Взаимная корреляция С++ и Matlab

Я пытаюсь сделать взаимную корреляцию на С++. Проблема в том, что я не получаю такой же результат в Matlab.

Код C++

float telo[5] = {-1, 0, 1, 2, 3};
Mat prueba(1, 5, CV_32F, telo);
float telo2[3] = { 0, 1, 2 };
Mat prueba2(1, 3, CV_32F, telo2);
Mat result;
matchTemplate(prueba, prueba2, result, CV_TM_CCORR);
Result: 2048.0004882812500 2.660783784765e-314#DEN -6.2774385622041925e+066

Код Matlab:

a = [-1,0,1,2,3]
b = [0,1,2]
xcorr2(a,b)
Result: -2 -1 2 5 8 3 0

Что я делаю не так?


person Krivers    schedule 18.08.2015    source источник


Ответы (1)


Когда я пробую ваш пример кода C++ с OpenCV 3, я получаю следующий результат, как и ожидалось:

2, 5, 8

Это то же самое, что решение Matlab, но без хвостов.


Изменить:

Чтобы получить тот же результат, что и в Matlab, вы можете добавить к входным данным некоторое дополнение нулями. Сделайте это вручную в ваших данных:

float telo[9] = {0, 0, -1, 0, 1, 2, 3, 0, 0};
Mat prueba(1, 9, CV_32F, telo);

Или более общим решением (которое также должно работать с 2D-данными) будет вызов

copyMakeBorder(prueba, prueba, prueba2.rows - 1, prueba2.rows - 1, prueba2.cols - 1, prueba2.cols - 1, cv::BORDER_CONSTANT);

до matchTemplate.

person Robert Hegner    schedule 18.08.2015
comment
Спасибо за ответ. Я использую opencv 2.49, так что это неправильная реализация или почему вывод отличается? Есть ли способ получить точно такой же результат, как у Matlab (с головой и хвостом последовательности)? - person Krivers; 18.08.2015
comment
Я не знаю, почему вы видите разные результаты. Вы пробовали именно тот код, который вы разместили, или это упрощенный пример? Я обновил свой ответ, чтобы объяснить, как получить хвосты. - person Robert Hegner; 18.08.2015
comment
Я скопировал точно такой же исходный код из моей основной функции и вставил его сюда. Есть ли какое-то правило, сколько нулей я должен использовать? Потому что Matlab сам делает заполнение. - person Krivers; 18.08.2015
comment
Да правило такое: прибавить (длина пруэба2 - 1) с каждой стороны. Мой вызов copyMakeBorder делает именно это. - person Robert Hegner; 18.08.2015