创建自己的线性过滤器

时间:2018-02-07 10:29:54

标签: c++ image opencv

我是Opencv C ++的新手。我试图用图像卷积一个掩码。为此,我想创建自己的蒙版,以便我可以使用filter2D数组函数将我的蒙版与图像进行卷积。我想创建的面具是:

char mask [3][3]=  {{-1,0,1},{-1,0,1},{-1,0,1}};

为此我尝试了下面的代码(生成这个掩码): -

Mat kernel(3,3, CV_8UC1, Scalar(-1,0,1)); 

我已将面具值打印为

std::cout << kernel;

但我得到的答案是       0,0,0;       0,0,0;       0,0,0

我期待得到答案    -1,0,1;    -1,0,1;    -1,0,1

我知道我在正确编写频道时犯了一个错误。任何人都可以帮助我理解通道(CV_8UC1 ....)的含义以及如何纠正它并获得正确的输出。

2 个答案:

答案 0 :(得分:3)

CV_8UC1表示1通道,8位,uchar图像。

标量用于设置每个通道的值,而不是每个像素/坐标。

例1:

PASSWORD$Passord <- as.character(PASSWORD$Passord)
PASSWORD$Passord[PASSWORD$Passord==pwd] <- input$password3 
PASSWORD$Passord <- as.factor(PASSWORD$Passord) 
write.csv(PASSWORD,"<PATH>",row.names=FALSE)

意味着创建一个带有0的3X3矩阵,因为它的类型为 CV_8UC1 ,所以只能提一个值,在本例中为0。

EX 2:

Mat kernel(3,3, CV_8UC1, Scalar::all(0)) 

表示创建一个包含3个通道的3X3矩阵,因为类型为 CV_8UC3 ,并将通道1设置为0,通道2设置为0,通道3设置为255.

因此,为了设置行值,您不能使用标量。 而是这样做:

Mat kernel(3,3, CV_8UC3, Scalar(0,0,255)) 

查看this了解详情。

希望这有帮助!

答案 1 :(得分:1)

您想为kernel创建negative filter2D元素,然后您不应使用CV_8UC1的数据类型。 There is no negative value in unsigned type

Mat kernel(3,3, CV_8UC1, Scalar(-1,0,1));表示创建一个signal-channel-unsigned-char内核。您将Scalar(-1,0,1)设置为kernel,然后仅使用the first element(that is double -1)saturate_cast<unchar>(-1) = 0

通常,请改用CV_32FC1

例如:

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

int main(){
    float mask[9] = {-1,0,1, -1, 0, 1, -1,0,1};
    Mat kernel(3,3, CV_32FC1);
    memcpy(kernel.data, mask, sizeof(float)*9);
    cout << kernel<<endl;
}

结果:

[-1, 0, 1;
 -1, 0, 1;
 -1, 0, 1]

类似的问题:

How to create cv::Mat from buffer (array of T* data) using a template function?