OpenCV基础API函数三

OpenCV基础API函数一

OpenCV基础API函数二

OpenCV基础API函数三

OpenCV基础API函数四

OpenCV基础API函数五

GaussianBlur 高斯模糊

void GaussianBlur( InputArray src, OutputArray dst, Size ksize,
                                double sigmaX, double sigmaY = 0,
                                int borderType = BORDER_DEFAULT );
返回值: 空
src:原图像
dst: 结果图像
ksize:模糊窗口的大小
sigmaX: X轴方向的卷积核标准差
sigmaY: Y轴方向的卷积核标准差,默认为零表示X=Y,当sigmaX,sigmaY同时为零的时候会从ksize中进行推算出sigmaX,sigmaY,
borderType: 边界处理方式

例子:利用你高斯模糊处理图片
在这里插入图片描述

void Demo::Gaussian_Blur(Mat &src){
    Mat dst;
    GaussianBlur(src, dst, Size(17, 17), 3);
    imshow("高斯模糊", dst);
    GaussianBlur(src, dst, Size(17, 17), 13);
    //ksize或sigmaX,sigmaY越大模糊程度越大
    imshow("高斯模糊1", dst);
}

bilateralFilter 双边模糊–美颜效果

void bilateralFilter( InputArray src, OutputArray dst, int d,
                                   double sigmaColor, double sigmaSpace,
                                   int borderType = BORDER_DEFAULT );
返回值:空
src:输入的原图像
dst:结果图像
d: 模糊的窗口的大小,如果为零 则从sigmaSpace中计算得出
sigmaColor:颜色控件的卷积核标准差
sigmaSpace:xy空间上面的卷积和标准差,当d>0不考虑sigmaSpace的大小
borderType :边界处理的模式

例子: 利用双边模糊对任务进行美颜
在这里插入图片描述

void Demo::mybilateralFilter(Mat &src){
    Mat dst;
    //双边模糊
    bilateralFilter(src,dst,0,100,10);
    imshow("高斯双边模糊1", dst);
}

相对于高斯模糊和均值模糊双边模糊有一个更大的优点,就是他能够保留图片中的边界 而不会把边界进行模糊从而达到美颜的效果

blur 卷积模糊

void blur( InputArray src, OutputArray dst,
                        Size ksize, Point anchor = Point(-1,-1),
                        int borderType = BORDER_DEFAULT );
返回值: 空
src:输入的圆图像
dst: 输出的结果图像
ksize: 卷积核的大小
anchor:卷积核的锚定点(中心点)
borderType: 边界处理模式

例子 对图像进行模糊

在这里插入图片描述

 	Mat dst;
    blur(src, dst, Size(9, 9));
    imshow("卷积模糊", dst);

copyMakeBorder 边界处理

void copyMakeBorder(InputArray src, OutputArray dst,
int top, int bottom, int left, int right,
int borderType, const Scalar& value = Scalar() );

返回值:空
src 输入的原图像
dst:输出的结果图像
top:插入顶边界的宽
bottom:插入底边界的宽
left:插入左边界的宽
right:插入右边界的宽
borderType:边界处理的方法
Scalar:颜色值
borderType意思
BORDER_CONSTANT对边界指定一个常数
BORDER_REPLICATE复制图形边上的一个像素填充到边界上 aaaaaa|abcdefgh|hhhhhhh
BORDER_REFLECT边界对图像进行映射 fedcba|abcdefgh|hgfedcb
BORDER_WRAP左右上下颠倒 把底边的像素填充到上边界,把上边的像素填充到地辩解 cdefgh
BORDER_REFLECT_101gfedcb|abcdefgh| gfedcba

在这里插入图片描述
由以上图骗我们可以看出各个方法区别所在

void Demo::myBlury(Mat &src){
    Mat dst;

    copyMakeBorder(src,dst,16,16,16,16,BORDER_CONSTANT,Scalar(0,0,255) );
    namedWindow("BORDER_CONSTANT", WINDOW_FREERATIO);
    imshow("BORDER_CONSTANT", dst);

    copyMakeBorder(src,dst,16,16,16,16,BORDER_REPLICATE    );
    namedWindow("BORDER_REPLICATE", WINDOW_FREERATIO);
    imshow("BORDER_REPLICATE", dst);

    copyMakeBorder(src,dst,16,16,16,16,BORDER_REFLECT  );
    namedWindow("BORDER_REFLECT", WINDOW_FREERATIO);
    imshow("BORDER_REFLECT", dst);

    copyMakeBorder(src,dst,16,16,16,16,BORDER_WRAP  );
    namedWindow("BORDER_WRAP", WINDOW_FREERATIO);
    imshow("BORDER_WRAP", dst);

    copyMakeBorder(src,dst,16,16,16,16,BORDER_REFLECT_101   );
    namedWindow("BORDER_REFLECT_101", WINDOW_FREERATIO);
    imshow("BORDER_REFLECT_101", dst);


    //blur(src, dst, Size(9, 9));
//    imshow("BORDER_CONSTANT ", dst);
}

LUT 颜色查找表—添加滤镜

void LUT(InputArray src, InputArray lut, OutputArray dst);

返回值:空
src:原图像
lut:颜色查找表大小为(256,1)的Mat数组
dst:结果图像

例子:给一个图片添加一个滤镜

在这里插入图片描述
我们用到的颜色条
请添加图片描述

void Demo::myLut(Mat &src,Mat &src1){

    Mat dst;
    cout << src.cols << endl;
    Mat myLut = Mat::zeros(256, 1, CV_8UC3);
//    填充颜色对照表
    for (int i = 0; i < 256; ++i)
    {
        myLut.at<Vec3b>(i, 0) = src1.at<Vec3b>(10, i);
    }
    //给原图像替换颜色对照表
    LUT(src, myLut, dst);
    namedWindow("添加滤镜",WINDOW_FREERATIO);
    imshow("添加滤镜", dst);
}

颜色查找表的意思就是我们首先建立一张颜色对照表,灰度从0~255,然后我们的图片根据这张表格进行进行替换颜色
在这里插入图片描述

filter2D 自定义滤波器

void filter2D( InputArray src, OutputArray dst, int ddepth,
                            InputArray kernel, Point anchor = Point(-1,-1),
                            double delta = 0, int borderType = BORDER_DEFAULT );
返回值:空
src:输入原图像
dst:输出结果图像
ddepth:图像的深度不同的卷积核图像的深度是不同的,-1表示和src的深度一样,当卷积核为小数是,深度为CV_32F,当卷积核为整数时深度为CV_32S
kernel:卷积核
anchor:卷积核的锚定点
dalta:当图像太暗是,添加他增加亮度
norderType:边界填充模式

例子:利用自定义滤波器模糊图像
在这里插入图片描述

void customFilter(Mat &src){

    Mat dst;
    //自定义卷积核
    Mat kernel=Mat::ones(15,15,CV_32F);
    //滤波函数
    filter2D(src, dst, CV_32S, kernel, Point(-1, -1), 127, BORDER_DEFAULT);

    namedWindow("模糊",WINDOW_FREERATIO);
    imshow("模糊", dst);
}

robot 梯度

robot梯度需要我们自定义算子,同时还需要我们利用自定义滤波器进行计算

在这里插入图片描述
例子:对一张图片执行robot算子
在这里插入图片描述
我们发现梯度可以很好的发先我的图片里面的边缘

void Demo::myCustomGrad(Mat &src)
{
	Mat dst;
    Mat dst_x, dst_y;
    //X轴方向的算子
    Mat robot_x=(Mat_<int>(2, 2) << 1,0,0,-1);
    //Y轴方向的算子
    Mat robot_y=(Mat_<int>(2, 2) << 0,1,-1,0);
    //我们对图像结果增加127是因为我们robot图像结果太暗
    filter2D(src, dst_x, CV_32F, robot_x,Point(-1,-1),127);
    filter2D(src, dst_y, CV_32F, robot_y,Point(-1,-1),127);
    //执行算子过会我们图像的灰度值在[-255,255]范围之间所以需要对灰度值取绝对值
    convertScaleAbs(dst_x, dst_x);
    convertScaleAbs(dst_y, dst_y);
   //为了放置放置图片相加之后图片发白我们采取addWighted方式进行相加
    addWeighted(dst_x,0.5,dst_y,0.5,0,dst);
    namedWindow("robot-输出", WINDOW_FREERATIO);
    imshow("robot-输出", dst);
 }

Sobel 梯度

void Sobel( InputArray src, OutputArray dst, int ddepth,
                         int dx, int dy, int ksize = 3,
                         double scale = 1, double delta = 0,
                         int borderType = BORDER_DEFAULT );
返回值:空
src:输入的图像
dst:输出的图像
ddpth:图像的深度,绝对不允许为8位的深度  需要CV_32F
dx:执行X轴方向的算子
dy:执行Y轴方向的算子,ds,dy同时只能有一个为1另一个为0
ksize:卷积窗口大小
scal:伸缩比例因子,正常情况下我们不应用伸缩比例因子
dalta:是否给结果图像增加亮度
borderType:边界填充方式

索贝尔梯度算子在opencv中已经集成好了,所以我们直接调用API函数

例子:执索贝尔算子
在这里插入图片描述
通过对比robot算子可以发现,Sobel算子发现边缘的能力更强

void Demo::myCustomGrad(Mat &src)
{
	Mat dst;
	Mat dst_x, dst_y;
	Sobel(src, dst_x, CV_32F, 1, 0);
    Sobel(src, dst_y, CV_32F, 0, 1);
    convertScaleAbs(dst_x, dst_x);
    convertScaleAbs(dst_y, dst_y);
    addWeighted(dst_x,0.5,dst_y,0.5,0,dst);
    namedWindow("Sobel-输出", WINDOW_FREERATIO);
    imshow("Sobel-输出", dst);

Scharr 梯度

void Scharr( InputArray src, OutputArray dst, int ddepth,
                          int dx, int dy, double scale = 1, double delta = 0,
                          int borderType = BORDER_DEFAULT );

Scharr的参数意思和Sobel完全一样

例子: 执行Scharr算子

在这里插入图片描述
Scharr算子发现图像边缘的能力大于Sobel

void Demo::myCustomGrad(Mat &src)
{
	Mat dst;
	Mat dst_x, dst_y;
	Scharr(src, dst_x, CV_32F, 1, 0);
    Scharr(src, dst_y, CV_32F, 0, 1);
    convertScaleAbs(dst_x, dst_x);
    convertScaleAbs(dst_y, dst_y);
    addWeighted(dst_x,0.5,dst_y,0.5,0,dst);
    namedWindow("Scharr-输出", WINDOW_FREERATIO);
    imshow("Scharr-输出", dst);
}

Laplacian 拉普拉斯梯度

void Laplacian( InputArray src, OutputArray dst, int ddepth,
                             int ksize = 1, double scale = 1, double delta = 0,
                             int borderType = BORDER_DEFAULT );
返回值:空
src:输入原图像
dst:输出结果图像
ddepth:输出结果图像的深度 -1表示和src的深度一样,但是应该使用CV_32F类型的深度
ksize:卷积核的窗口大小
scale:缩放比例因子
delta:结果图像增加的值
borderType:边界填充方式

拉普拉斯算子发线边缘的能力大于Scharr算子

例子:执行laplacian算子
在这里插入图片描述

void Demo::myCustomGrad(Mat &src)
{
	Mat dst;
	Laplacian(src, dst, -1,3);
    namedWindow("Laplacian-输出", WINDOW_FREERATIO);
    imshow("Laplacian-输出", dst);
}

消除美颜 - - - 拉普拉斯锐化

例子:执行锐化算子—消除美颜
在这里插入图片描述

void Demo::myCustomGrad(Mat &src)
{
	Mat dst;
	//拉普拉斯锐化算子
    Mat kernel=(Mat_<int>(3,3) <<
            0,-1,0,
            -1,5-1,
            0,-1,0);
    filter2D(src, dst, CV_32F, kernel, Point(-1, -1));
    convertScaleAbs(dst,dst);

    namedWindow("Laplacian锐化-输出", WINDOW_FREERATIO);
    imshow("Laplacian锐化-输出", dst);

}

随机产生椒盐噪声

无API

椒盐噪声是一种在图像中随机出现的黑白像素点要么是(0,0,0)要么是(255,255,255),去除椒盐噪声我们可以使用中值滤波

例子:随机创建2W个椒盐噪声
在这里插入图片描述

void creatNoise(Mat &src){
    //产生随机数种子
    srand(time(NULL));
    int row = src.rows;
    int col=src.cols;
    //产生2W个噪声点
    for (int i = 0; i < 20000; ++i)
    {
        //获取随机位置
        int r = rand() % row;
        int c = rand() % col;
        //若取余为零则产生黑点否则为白点
        if (i % 2 == 0)
        {
            src.at<Vec3b>(r, c)=Vec3b(0,0,0);
        }
        else{
            src.at<Vec3b>(r, c)=Vec3b(255,255,255);
        }
    }
    namedWindow("椒盐噪声", WINDOW_FREERATIO);
    imshow("椒盐噪声", src);

}

创建高斯噪声

randn: 利用均值和标准差向矩阵中填充正态分布随机数---生成随机图像

void randn(InputOutputArray dst, InputArray mean, InputArray stddev);
返回值:空
mean:平均值
stddev:标准差

例子:产生高斯噪声
在这里插入图片描述

void Demo::creatNoise(Mat &src)
{


    //生成的噪声图像和原图像大小类型相同
    Mat gaussianNoise = Mat::zeros(src.size(), src.type());
    //产生随机数矩阵,利用提供的均值和方差进行生成矩阵
    randn(gaussianNoise, Scalar(25, 25, 25), Scalar(50, 50, 50));
    namedWindow("随机高斯噪声", WINDOW_FREERATIO);
    imshow("随机高斯噪声", gaussianNoise);

    addWeighted(src, 1, gaussianNoise, 1, 0, src);
    namedWindow("高斯噪声", WINDOW_FREERATIO);
    imshow("高斯噪声", src);

}

medianBlur 中值滤波—消除椒盐噪声

void medianBlur( InputArray src, OutputArray dst, int ksize );
返回值:空
src:输出图像
dst:输出图像
ksize:卷积核窗口大小---基本上为奇数

中值滤波: 是一种排序滤波; 首先对卷积核窗口内的像素进行排序选择中值填充到窗口中心位置
在这里插入图片描述
例子:去除椒盐噪声
在这里插入图片描述

// 产生随机数种子
    Mat dst;
    srand(time(NULL));
    int row = src.rows;
    int col=src.cols;
    //产生2W个噪声点
    for (int i = 0; i < 20000; ++i)
    {
        //获取随机位置
        int r = rand() % row;
        int c = rand() % col;
        //若取余为零则产生黑点否则为白点
        if (i % 2 == 0)
        {
            src.at<Vec3b>(r, c)=Vec3b(0,0,0);
        }
        else{
            src.at<Vec3b>(r, c)=Vec3b(255,255,255);
        }
    }
    namedWindow("椒盐噪声", WINDOW_FREERATIO);
    imshow("椒盐噪声", src);


    //中值滤波--去除椒盐噪声
    medianBlur(src, dst, 3);
    namedWindow("消除椒盐噪声", WINDOW_FREERATIO);
    imshow("消除椒盐噪声", dst);

Canny 边缘提取

void Canny( InputArray image, OutputArray edges,
                         double threshold1, double threshold2,
                         int apertureSize = 3, bool L2gradient = false );
返回值:空
edges:边缘图像
threshold1:最小阈值
threshold2:最大阈值
apertureSize:Sobel 算子卷积核窗口的大小
L2gradient :是否使二阶导数的梯度

边缘提取规则:

1.首先采用Sobel算子对图像进行模糊
2标记出小于最小阈值的像素`(丢弃)`大于最大阈值的像素`(边界)`和在最大最小阈值中间的像素`(用于连接边缘)`

例子:图像边缘
在这里插入图片描述

//tracBar回调函数
void edgesTrackbar(int pos, void *userdata){
    Mat dst;
    Mat src = *(Mat *) userdata;
    Canny(src, dst, pos, pos * 3, 3, true);
    imshow("边缘提取", dst);
}

void Demo::myEdges(Mat &src){

    namedWindow("边缘提取", WINDOW_FREERATIO);
    int value = 20;
    createTrackbar("阈值", "边缘提取", &value, 300, edgesTrackbar, &src);
    edgesTrackbar(20, &src);
}

OTSU阈值 平均阈值和三角法阈值 二值化

void MyThreshold(Mat &src)
{
    Mat dst;
    //获取平均值
    if (src.channels() >= 3)
    {
        cvtColor(src, src, COLOR_BGR2GRAY);
    }
    namedWindow("灰度图像", WINDOW_FREERATIO);
    imshow("灰度图像", src);
    //平均阈值
    Scalar m = mean(src);
    cout << "平均值 " << m[0] << endl;
    threshold(src, dst, m[0], 255, THRESH_BINARY);
    namedWindow("基于平均值 二值图像分割", WINDOW_FREERATIO);
    imshow("基于平均值 二值图像分割", dst);

    double T = 0;
    //otsu全局阈值
    T = threshold(src, dst, 0, 255, THRESH_BINARY | THRESH_OTSU);
    namedWindow("基于OTSU 二值图像分割", WINDOW_FREERATIO);
    imshow("基于OTSU 二值图像分割", dst);
    cout << "OTSU " << T << endl;

    //三角法
    T = threshold(src, dst, 0, 255, THRESH_BINARY | THRESH_TRIANGLE);
    namedWindow("基于三角法 二值图像分割", WINDOW_FREERATIO);
    imshow("基于三角法 二值图像分割", dst);
    cout << "三角法 " << T << endl;
}

adaptiveThreshold 自适应阈值二值化

自适应阈值二值化比较适合处理光照不均的图片

void adaptiveThreshold( InputArray src, OutputArray dst,
                                     double maxValue, int adaptiveMethod,
                                     int thresholdType, int blockSize, double C );
返回值:空
src:输入灰度图像
dst:结果图像
maxValue:二值图像的最大值
adaptiveMethod:自适应阈值算法 包括高斯算法,均值算法
thresholdType:二值化算法
blockSize:自适应阈值的窗口大小
C:加权的常数

例子:二值化图像
在这里插入图片描述

void adaptiveThresholdMonth(int pos,void *use)
{
    Mat dst;
    Mat src = *(Mat *) use;
    if(src.channels()>=3)
    {
        cvtColor(src, src, COLOR_BGR2GRAY);
    }
    adaptiveThreshold(src, dst, 255, ADAPTIVE_THRESH_GAUSSIAN_C, THRESH_BINARY, 5, pos);
    imshow("自适应阈值", dst);
}

void Demo::YadapterThreshold(Mat &src){
    namedWindow("自适应阈值", WINDOW_FREERATIO);
    int value = 10;
    createTrackbar("增量", "自适应阈值", &value, 80, adaptiveThresholdMonth, &src);
    adaptiveThresholdMonth(value, &src);
}
  • 0
    点赞
  • 10
    收藏
    觉得还不错? 一键收藏
  • 打赏
    打赏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

~搬~运~工~

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值