OpenCV CalcCovarMatrix vs. Numpy Cov

时间:2016-06-30 08:08:36

标签: python c++ opencv numpy

我正在将图像处理算法从Python移植到C ++,在两种情况下都使用OpenCV。

在Python版本中,我们使用Numpy的np.cov:

import numpy as np
#Using some dummy data to represent BGR pixels
values = [[30, 37, 35], [26, 36, 34], [38, 45, 41], [40, 47, 43], [38, 45, 43], [34, 43, 40], [30, 39, 37]]
result = np.cov(values, rowvar=False) #Using default 1/(N-1) normalisation
print result

产生输出:

[[ 27.23809524  22.23809524  18.66666667]
 [ 22.23809524  18.9047619   15.83333333]
 [ 18.66666667  15.83333333  13.66666667]]

在C ++版本中,我们使用OpenCV中的calcCovarMatrix:

#include <opencv2/core.hpp>
#include <iostream>
using namespace std;
using namespace cv;

int main() {
  Mat values(7, 3, CV_8UC1);
  //Representing the same pixels as the Python code
  values.at<uchar>(0) = (30, 37, 35);
  values.at<uchar>(1) = (26, 36, 34);
  values.at<uchar>(2) = (38, 45, 41);
  values.at<uchar>(3) = (40, 47, 43);
  values.at<uchar>(4) = (38, 45, 43);
  values.at<uchar>(5) = (34, 43, 40);
  values.at<uchar>(6) = (30, 39, 37);

  Mat avgs, covars;
  calcCovarMatrix(values, covars, avgs, CV_COVAR_NORMAL | CV_COVAR_SCALE | CV_COVAR_ROWS);
  cout << covars << "\n";
  calcCovarMatrix(values, covars, avgs, CV_COVAR_NORMAL | CV_COVAR_ROWS);
  cout << covars << "\n";

  return 0;
}

产生输出:

[364.8163265306122, 253.4285714285715, 260.6122448979592;
 253.4285714285715, 308.2857142857143, 317.5714285714286;
 260.6122448979592, 317.5714285714286, 334.8163265306122]
[2553.714285714286, 1774, 1824.285714285714;
 1774, 2158, 2223;
 1824.285714285714, 2223, 2343.714285714285]

可以看出,C ++输出根本不匹配Python输出。在calcCovarMatrix中缩放与否似乎无法纠正它,在np.cov中设置ddof或不设置似乎也无法纠正它。有什么想法吗?

注意:无论出于何种原因,np.cov和calcCovarMatrix使用“row”的矛盾解释;在两个输入案例中,每个代表一个观察,每个代表一个变量,所以在Numpy中我们设置rowvar = False但在calcCovarMatrix中我们设置CV_COVAR_ROWS(为True) )。我不认为这是问题的根源。

1 个答案:

答案 0 :(得分:1)

罪魁祸首已被确定!有两个问题:

1)values.at<uchar>(0) = (30, 37, 35);实际上并没有将值写入行(因为有人会从Python进入)。它实际上只是将最后一个值35写入Mat的第0个位置。上面代码中的Mat实际上解析为:

`[35,  34,  41;
  43,  43,  40;
  37,   0,   0;
   0,   0,   0;
   0,   0,   0;
   0,   0,   0;
   0,   0,   0]`

2)OpenCV CalcCovarMatrix未规范化。 covars/(values.rows-1)修复此问题并生成与Python Numpy相同的输出。