我有一个带有imfilter的matlab代码。现在我想把它转换成c++。我在这里读到的但是我无法用openCV3.3实现filterEngine(现在已经没有filterEngine了(。
这就是matlab中的滤波器:
imfilter(im2double(image),k,'same','replicate');
这是我的内核k:
k = fspecial('disk',3)
这一行的结果是一个值在0-1之间的7x7矩阵。
所以过滤器得到一个输入图像。它的值介于0和1之间(im2double(。所以我必须将我的8位图像转换到这个范围,我认为它的工作原理是这样的:
cv::normalize(inImage,outImage,0,1,cv::NORM_MINMAX);
然后使用内核对图像进行过滤。最后,我想再次输出一个8位的图像。
所以我想把两个给定的Matlab行转换成C++
我在链接中看到,你不能简单地使用filter2D。但是我该怎么做呢?有人知道吗?
++++编辑++++(测试zteffi的代码片段(
我已经测试了代码。到目前为止,结果是不同的。
内核的结构";磁盘";wis有点不同(更多的零(。其中的值也与Matlab中的值不同。
Matlabkernel:
0 0.000280919186665314 0.0110250278796606 0.0171905962763014 0.0110250278796606 0.000280919186665314 0
0.000280919186665314 0.0245167426505023 0.0353677651315323 0.0353677651315323 0.0353677651315323 0.0245167426505023 0.000280919186665314
0.0110250278796606 0.0353677651315323 0.0353677651315323 0.0353677651315323 0.0353677651315323 0.0353677651315323 0.0110250278796606
0.0171905962763014 0.0353677651315323 0.0353677651315323 0.0353677651315323 0.0353677651315323 0.0353677651315323 0.0171905962763014
0.0110250278796606 0.0353677651315323 0.0353677651315323 0.0353677651315323 0.0353677651315323 0.0353677651315323 0.0110250278796606
0.000280919186665314 0.0245167426505023 0.0353677651315323 0.0353677651315323 0.0353677651315323 0.0245167426505023 0.000280919186665314
0 0.000280919186665314 0.0110250278796606 0.0171905962763014 0.0110250278796606 0.000280919186665314 0
c++内核:
[0, 0, 0, 0.0303030303030303, 0, 0, 0;
0, 0.0303030303030303, 0.0303030303030303, 0.0303030303030303, 0.0303030303030303, 0.0303030303030303, 0;
0.0303030303030303, 0.0303030303030303, 0.0303030303030303, 0.0303030303030303, 0.0303030303030303, 0.0303030303030303, 0.0303030303030303;
0.0303030303030303, 0.0303030303030303, 0.0303030303030303, 0.0303030303030303, 0.0303030303030303, 0.0303030303030303, 0.0303030303030303;
0.0303030303030303, 0.0303030303030303, 0.0303030303030303, 0.0303030303030303, 0.0303030303030303, 0.0303030303030303, 0.0303030303030303;
0, 0.0303030303030303, 0.0303030303030303, 0.0303030303030303, 0.0303030303030303, 0.0303030303030303, 0;
0, 0, 0, 0.0303030303030303, 0, 0, 0]
我不知道这些值是如何在matlab中计算的。
下面的行应该创建一个";"圆圈";tha矩阵中值的。但在行维度中,边上有3*2个零,列维度中有2*2个零。但每个角落应该只有一个零。
Mat kernel = cv::getStructuringElement(cv::MORPH_ELLIPSE, cv::Size(radius * 2 + 1, radius * 2 + 1));
fspecial('disk',3)
的等价物是cv::getStructuringElement(cv::MORPH_ELLIPSE, cv::Size(radius * 2 + 1, radius * 2 + 1))
,除以内核的和,所以总和等于1。所以类似于:
Mat m = cv::imread("lena.jpg");
int radius = 3;
Mat kernel = cv::getStructuringElement(cv::MORPH_ELLIPSE, cv::Size(radius * 2 + 1, radius * 2 + 1));
double sum = cv::sum(cv::sum(kernel))[0]; // use cv::sum twice to get sum of all elements
kernel.convertTo(kernel, CV_64F, 1 / sum);
cv::filter2D(m, m, CV_64F, kernel);
m.convertTo(m, CV_8U);
您不需要将图像转换为<0、1>范围,除非你需要显示它。在这种情况下,你也不需要把它转换成双行,并把最后两行换成:
cv::filter2D(m, m, CV_8U, kernel);
您可以通过在编辑器中的函数名称上单击鼠标右键并选择"打开"函数名";菜单中的项。它将显示函数的matlab代码,您可以将其准确地移植到C++。