900字范文,内容丰富有趣,生活中的好帮手!
900字范文 > opencv实战2-修改保存图片 像素操作

opencv实战2-修改保存图片 像素操作

时间:2021-04-09 07:58:43

相关推荐

opencv实战2-修改保存图片 像素操作

1 加载修改保存图像

1.1 修改图像

opencv中 灰度图像由常量 CV_8U 表示 C++ 中的 unsigned char;

三通道图像由常量 CV_8UC3 表示;

1.2 保存图像

#include<stdio.h>#include <cstdio> #include <iostream>#include <opencv2/opencv.hpp>#include <opencv2/highgui.hpp>using namespace cv;using namespace std;int main() {Mat image;image = cv::imread("F:/project/OPENCV_TEST_PROJECT/picture/test.jpg");if (image.empty()) {cout << "error";return 0;}cv::namedWindow("Original Image");cv::imshow("Original Image",image);Mat result;cv::flip(image,result,1);//反转图片 正数表示水平 ;0 表示垂直;负数表示水平和垂直cv::namedWindow("Flip Image");cv::imshow("Flip Image", result);cv::imwrite("F:/project/OPENCV_TEST_PROJECT/picture/flip.jpg", result);//保存结果cv::waitKey(0);//0 表示等待按键}

1.3 在图片上绘制形状或添加文字

#include<stdio.h>#include <cstdio> #include <iostream>#include <opencv2/opencv.hpp>#include <opencv2/highgui.hpp>using namespace cv;using namespace std;int main() {Mat image;image = cv::imread("F:/project/OPENCV_TEST_PROJECT/picture/test.jpg");if (image.empty()) {cout << "error";return 0;}cv::namedWindow("Original Image");cv::imshow("Original Image",image);cv::circle(image, cv::Point(155, 110), //中心点坐标55, //半径0, //颜色3);//厚度cv::namedWindow("Result Image");cv::imshow("Result Image", image);cv::waitKey(0);//0 表示等待按键}

可使用 cv::putText 函数在图片上添加文字。

1.4 定义感兴趣区域ROI

#include<stdio.h>#include <cstdio> #include <iostream>#include <opencv2/opencv.hpp>#include <opencv2/highgui.hpp>using namespace cv;using namespace std;int main() {Mat image;image = cv::imread("F:/project/OPENCV_TEST_PROJECT/picture/test.jpg");if (image.empty()) {cout << "error";return 0;}//创建一个240*330 红色图像 通道是bgrMat image2(500,330,CV_8UC3,cv::Scalar(0,0,255));//在图像的右下角定义一个感兴趣区域Mat imageROI(image,cv::Rect(image.cols - image2.cols, //ROI坐标image.rows - image2.rows,image2.cols, image2.rows)); //ROI 大小//插入image2.copyTo(imageROI);cv::namedWindow("Original Image");cv::imshow("Original Image", image);cv::waitKey(0);//0 表示等待按键}

显示效果如下所示,原图上增加 红色矩阵:

2 像素操作

2.1 使用指针的方式操作图像

获取一行像素值的字节数

int nc = image.cols * images.channels();

返回一行元素的起始地址

uchar * data = image.ptr<uchar>(j);//j为第j行的地址

操作像素的字节

*data = *data/8;

对原图像进行拷贝

cv::Mat iamgeClone = image.clone();//图像的深拷贝

使用迭代器遍历图像元素

cv::Mat<cv::Vec3b>::iterator it = image.begin<cv::Vec3b>();cv::Mat<cv::Vec3b>::iterator itend = image.end<cv::Vec3b>();for(;it!=itend;++it){(*it)[0] = 112;//[]中访问元素通道(*it)[1] = 255;//[]中访问元素通道(*it)[2] = 255;//[]中访问元素通道}

2.2 访问图像元素

生成椒盐噪声:

#include<stdio.h>#include <cstdio> #include <iostream>#include <opencv2/opencv.hpp>#include <opencv2/highgui.hpp>using namespace cv;using namespace std;#include <random>void salt(cv::Mat image, int n) { //待处理如下,生成的椒盐噪声数量std::random_device seed_device;std::default_random_engine engine(seed_device());//通过operator()取得设备产生的随机值std::uniform_int_distribution<int> distrRow(0, image.rows -1);//10到100,int类型,线性分布std::uniform_int_distribution<int> distrCols(0, image.cols - 1);//10到100,int类型,线性分布int i, j;for (int k = 0; k < n; k++) {i = distrRow(engine);j = distrCols(engine);if (image.type() == CV_8UC1) { //灰度图image.at<uchar>(i, j) = 255;}else if (image.type() == CV_8UC3) { //灰度图image.at<cv::Vec3b>(i, j)[0] = 255;image.at<cv::Vec3b>(i, j)[1] = 255;image.at<cv::Vec3b>(i, j)[2] = 255;}}engine.seed(); //将引擎设为初始化状态cv::namedWindow("Original Image");cv::imshow("Original Image", image);}

使用Mat.at方法访问元素,at方法被实现成一个模板方法,调用时必须指定图像元素的类型。

image.at<cv::Vec3b>(i, j)[0] = 255;

2.3 计算某段代码运行的时间

const int64 start = cv::getTickCount();//获取计算机开机到当前的时钟周期数//运行一段代码double duration = (cv::getTickCount()-start)/cv::getTickFrequency();//换算为以秒为单位

2.4 扫描图像并访问相邻元素

滤波函数 cv::filter2D,定义内核kernel

void sharpen2D(const cv::Mat &image,cv::Mat &result){cv::Mat kernel(3,3,CV_32F,cv::Scalar(0));//构造内核,所有入口初始化为0//对内核赋值kernel.at<float>(1,1)=5.0;kernel.at<float>(0,1)=-1.0;kernel.at<float>(2,1)=-1.0;kernel.at<float>(1,0)=-1.0;kernel.at<float>(1,2)=-1.0;//对图像滤波操作cv::filter2D(image,result,image.depth(),kernel);}

本内容不代表本网观点和政治立场,如有侵犯你的权益请联系我们处理。
网友评论
网友评论仅供其表达个人看法,并不表明网站立场。