c++實(shí)現(xiàn)圖像像素計(jì)算的示例詳解
我們知道每張圖像都能夠用矩陣來表示,矩陣中每個元素的值表示了圖像中每個像素值,像素值的大小就對應(yīng)著圖像的亮暗。因此找到矩陣中的最大值,就是找到了圖像中灰度值最大的像素,計(jì)算矩陣所有元素的平均值就是計(jì)算圖像像素平均灰度,平均灰度表示圖像整體的亮暗程度。
圖像像素計(jì)算有以下幾種:
1、尋找圖像中最大像素值和最小像素值
可以利用opencv的minMaxLoc()函數(shù)實(shí)現(xiàn)
void cv::minMaxLoc(InputArray src, double * minVal, double * maxVal = 0, Point * minLoc = 0, Point * maxLoc = 0, InputArray mask = noArray())
src:需要尋找最大值和最小值的圖像或者矩陣,要求必須是單通道矩陣
- minVal:圖像或者矩陣中的最小值。
- maxVal:圖像或者矩陣中的最大值。
- minLoc:圖像或者矩陣中的最小值在矩陣中的坐標(biāo)。
- maxLoc:圖像或者矩陣中的最大值在矩陣中的坐標(biāo)。
- mask:掩模,用于設(shè)置在圖像或矩陣中的指定區(qū)域?qū)ふ易钪怠?/li>
Point數(shù)據(jù)類型是用于表示圖像的像素坐標(biāo),由于圖像的像素坐標(biāo)軸以左上角為坐標(biāo)原點(diǎn),水平方向?yàn)閤軸,垂直方向?yàn)閥軸,因此Point(x,y)對應(yīng)于圖像的行和列表示為Point(列數(shù),行數(shù))。在OpenCV中對于2D坐標(biāo)和3D坐標(biāo)都設(shè)置了多種數(shù)據(jù)類型,針對2D坐標(biāo)數(shù)據(jù)類型定義了整型坐標(biāo)cv::Point2i(或者cv::Point)、double型坐標(biāo)cv::Point2d、浮點(diǎn)型坐標(biāo)cv::Point2f,對于3D坐標(biāo)同樣定義了上述的坐標(biāo)數(shù)據(jù)類型,只需要將其中的數(shù)字“2”變成“3”即可。對于坐標(biāo)中x、y、z軸的具體數(shù)據(jù),可以通過變量的x、y、z屬性進(jìn)行訪問,例如Point.x可以讀取坐標(biāo)的x軸數(shù)據(jù)。
對于多通道矩陣數(shù)據(jù),利用cv::Mat::reshape()將多通道變成單通道,或者分別尋找每個通道的最值,然后再進(jìn)行比較尋找到全局最值。
具體使用案例如下:
#include<iostream> #include<vector> #include<string> #include <opencv2/opencv.hpp> #include "opencv/highgui.h" using namespace std; using namespace cv; int main(int argc,char** argv) { cout<<"OpenCv Version: "<<CV_VERSION<<endl;//輸出使用的opencv版本號 Mat img=imread('1.jpg');//單通道圖像 Mat imgs=imread("2.jpg");//多通道圖像 double minVal,maxVal;//用于存放矩陣中的最大值和最小值 Point minIdx,maxIdx;//用于存放矩陣中的最大值和最小值的位置 /*尋找單通道矩陣中的最值*/ minMaxLoc(img,&maxVal,&minVal,&minIdx,&maxIdx); cout << "img中最大值是:" << maxVal << " " << "在矩陣中的位置:" << maxIdx << endl; cout << "img中最小值是:" << minVal << " " << "在矩陣中的位置:" << minIdx << endl; /*尋找多通道矩陣中的最值*/ Mat imgs_re=imgs.reshape(1,4);//將多通道矩陣變成單通道矩陣 minMaxLoc(imgs_re,&minVal,&maxVal,&minIdx,&maxIdx); cout << "img中最大值是:" << maxVal << " " << "在矩陣中的位置:" << maxIdx << endl; cout << "img中最小值是:" << minVal << " " << "在矩陣中的位置:" << minIdx << endl; return 0; }
2、計(jì)算圖像的均值和標(biāo)準(zhǔn)差
如果我們想知道圖像的亮暗程度變化,可以求圖像的均值來判斷。均值越大,說明圖像越亮。圖像標(biāo)準(zhǔn)差表示圖像中明暗變化程度,標(biāo)準(zhǔn)差越大表示圖像中明暗變化越明顯。
我們可以利用cv::mean()函數(shù)用于計(jì)算圖像的平均值,也可以利用meanStdDev()函數(shù)用于同時計(jì)算圖像的均值和標(biāo)準(zhǔn)方差。
cv::Scalar cv::mean(InputArray src,InputArray mask = noArray())
- src:待求平均值的圖像矩陣。
- mask:掩模,用于標(biāo)記求取哪些區(qū)域的平均值。
該函數(shù)用來求取圖像矩陣的每個通道的平均值,函數(shù)的第一個參數(shù)用來輸入待求平均值的圖像矩陣,其通道數(shù)目可以在1到4之間。需要注意的是,該函數(shù)的返回值是一個cv::Scalar類型的變量,函數(shù)的返回值有4位,分別表示輸入圖像4個通道的平均值,如果輸入圖像只有1個通道,那么返回值的后三位都為0,例如輸入該函數(shù)一個單通道平均值為1的圖像,輸出的結(jié)果為[1,0,0,0],可以通過cv::Scalar[n]查看第n個通道的平均值。該函數(shù)的第二個參數(shù)用于控制圖像求取均值的范圍,在第一個參數(shù)中去除第二個參數(shù)中像素值為0的像素,當(dāng)不輸入第二個參數(shù)時,表示求取第一個參數(shù)全部像素的平均值。
void cv::meanStdDev(InputArray src,OutputArray mean,OutputArray stddev,InputArray mask = noArray())
- src:待求平均值的圖像矩陣。
- mean:圖像每個通道的平均值,參數(shù)為Mat類型變量。
- stddev:圖像每個通道的標(biāo)準(zhǔn)方差,參數(shù)為Mat類型變量。
- mask:掩模,用于標(biāo)記求取哪些區(qū)域的平均值和標(biāo)準(zhǔn)方差。
該函數(shù)的第一個參數(shù)與前面mean()函數(shù)第一個參數(shù)相同,都可以是1-4通道的圖像,不同之處在于該函數(shù)沒有返回值,圖像的均值和標(biāo)準(zhǔn)方差輸出在函數(shù)的第二個和第三個參數(shù)中,區(qū)別于mean()函數(shù),用于存放平均值和標(biāo)準(zhǔn)方差的是Mat類型變量,變量中的數(shù)據(jù)個數(shù)與第一個參數(shù)通道數(shù)相同,如果輸入圖像只有一個通道,該函數(shù)求取的平均值和標(biāo)準(zhǔn)方差變量中只有一個數(shù)據(jù)。
具體使用案例如下:
#include<iostream> #include<vector> #include<string> #include <opencv2/opencv.hpp> #include "opencv/highgui.h" using namespace std; using namespace cv; int main(int argc,char** argv) { cout<<"OpenCv Version: "<<CV_VERSION<<endl; Mat img=imread("3.jpg");//單通道圖像或矩陣 Mat imgs=imread("4.jpg");//多通道圖像或矩陣 cout << "/* 用meanStdDev同時求取圖像的均值和標(biāo)準(zhǔn)方差 */" << endl; Scalar myMean; myMean=mean(imgs); cout<<"imgs均值 = "<<myMean<<endl; cout<<"imgs第一個通道的均值 = "<<myMean[0]<<" " <<"imgs第二個通道的均值 = "<<myMean[1]<<endl; cout << "/* 用meanStdDev同時求取圖像的均值和標(biāo)準(zhǔn)方差 */" << endl; Mat myMeanMat,myStddevMat; meanStdDev(img,myMeanMat,myStddevMat); cout << "img均值=" << myMeanMat << " " << endl; cout << "img標(biāo)準(zhǔn)方差=" << myStddevMat << endl << endl; meanStdDev(imgs,myMeanMat,myStddevMat); cout << "img均值=" << myMeanMat << " " << endl; cout << "img標(biāo)準(zhǔn)方差=" << myStddevMat << endl << endl; return 0; }
3、兩張圖像比較運(yùn)算
opencv提供了求取兩張圖像每一位像素較大或者較小灰度值的max()、min()函數(shù),這兩個函數(shù)分別比較兩個圖像中每一位元素灰度值的大小,保留較大(較?。┑幕叶戎怠?/p>
void cv::max(InputArray src1,InputArray src2,OutputArray dst) void cv::min(InputArray src1,InputArray src2,OutputArray dst)
- src1:第一個圖像矩陣,可以是任意通道數(shù)的矩陣。
- src2:第二個圖像矩陣,尺寸和通道數(shù)以及數(shù)據(jù)類型都需要與src1一致。
- dst:保留對應(yīng)位置較大(較?。┗叶戎岛蟮膱D像矩陣,尺寸、通道數(shù)和數(shù)據(jù)類型與src1一致
該函數(shù)的功能相對來說比較簡單,就是比較圖像每個像素的大小,按要求保留較大值或者較小值,最后生成新的圖像。
具體案例如下:
#include<iostream> #include<vector> #include<string> #include <opencv2/opencv.hpp> #include "opencv/highgui.h" using namespace std; using namespace cv; int main(int argc,char** argv) { cout<<"OpenCv Version: "<<CV_VERSION<<endl; //對兩張彩色圖像進(jìn)行比較運(yùn)算 Mat img1=imread("l.png"); Mat img2=imread("2.jpg"); if(img0.empty()||img1.empty()){ cout<<"請確認(rèn)圖像文件名稱是否正確"<<endl; return -1; } Mat comMin,comMax; max(img1,img2,comMax); min(img1,img2,comMin); imshow("comMin",comMin); imshow("comMax",comMax); //與掩模進(jìn)行比較運(yùn)算 Mat src1=Mat::zeros(Size(512,512),CV_8UC3); Rect rect(100,100,300,300);//起點(diǎn)(100,100)長300,寬300的矩形 src1(rect)=Scalar(255,255,255);//生成一個300*300的掩模 Mat comsrc1,comsrc2; min(img1,src1,comsrc1); imshow("comsrc1",comsrc1); Mat src2=Mat(512,512,CV_8UC3,Scalar(0,0,255));//生成一個顯示紅色的低通掩模 min(img1,src2,comsrc2); imshow("comsrc2",comsrc2); //對兩張圖片灰度圖像進(jìn)行比較運(yùn)算 Mat img1g,img2g,comMing,comMaxg; cvtColor(img1,img1g,COLOR_BGR2GRAY); cvtColor(img2,img2g,COLOR_BGR2GRAY); max(img1g,img2g,comMaxg); max(img1g,img2g,comMaxg); imshow("comMing",comMing); imshow("comMaxg",comMaxg); return 0; }
4、圖片邏輯運(yùn)算
opencv為兩個圖像像素之間邏輯運(yùn)算與、或、異或以及非運(yùn)算提供了bitwise_and()、bitwise_or()、bitwise_xor()和bitwise_not()四個函數(shù),在進(jìn)行邏輯計(jì)算時,一定要保證兩個圖像矩陣之間的尺寸、數(shù)據(jù)類型和通道數(shù)相同,多個通道進(jìn)行邏輯運(yùn)算時不同通道之間是獨(dú)立進(jìn)行的。
具體案例如下:
#include <opencv2\opencv.hpp> #include <iostream> #include <vector> using namespace std; using namespace cv; int main() { Mat img = imread("lena.png"); if (img.empty()) { cout << "請確認(rèn)圖像文件名稱是否正確" << endl; return -1; } //創(chuàng)建兩個黑白圖像 Mat img0 = Mat::zeros(200, 200, CV_8UC1); Mat img1 = Mat::zeros(200, 200, CV_8UC1); Rect rect0(50, 50, 100, 100); img0(rect0) = Scalar(255);//將起點(diǎn)50,50,長寬100的矩形框區(qū)域像素值置為255,白色 Rect rect1(100, 100, 100, 100); img1(rect1) = Scalar(255); imshow("img0", img0); imshow("img1", img1); //進(jìn)行邏輯運(yùn)算 Mat myAnd, myOr, myXor, myNot, imgNot; bitwise_not(img0, myNot); bitwise_and(img0, img1, myAnd); bitwise_or(img0, img1, myOr); bitwise_xor(img0, img1, myXor); bitwise_not(img, imgNot); imshow("myAnd", myAnd); imshow("myOr", myOr); imshow("myXor", myXor); imshow("myNot", myNot); imshow("img", img); imshow("imgNot", imgNot); waitKey(0); return 0; }
到此這篇關(guān)于c++實(shí)現(xiàn)圖像像素計(jì)算的示例詳解的文章就介紹到這了,更多相關(guān)c++圖像像素計(jì)算內(nèi)容請搜索腳本之家以前的文章或繼續(xù)瀏覽下面的相關(guān)文章希望大家以后多多支持腳本之家!
相關(guān)文章
詳解C語言中sizeof如何在自定義函數(shù)中正常工作
在main函數(shù)中,sizeof是可以正常工作的,但是在自定義函數(shù)中就不可以了。所以本文將為大家詳細(xì)講解一下如何解決這一問題,感興趣的可以了解一下2022-05-05C語言實(shí)現(xiàn)航空訂票系統(tǒng)課程設(shè)計(jì)
這篇文章主要為大家詳細(xì)介紹了C語言實(shí)現(xiàn)航空訂票系統(tǒng)課程設(shè)計(jì),文中示例代碼介紹的非常詳細(xì),具有一定的參考價值,感興趣的小伙伴們可以參考一下2022-03-03C++?Boost?Accumulators累加器詳細(xì)講解
Boost是為C++語言標(biāo)準(zhǔn)庫提供擴(kuò)展的一些C++程序庫的總稱。Boost庫是一個可移植、提供源代碼的C++庫,作為標(biāo)準(zhǔn)庫的后備,是C++標(biāo)準(zhǔn)化進(jìn)程的開發(fā)引擎之一,是為C++語言標(biāo)準(zhǔn)庫提供擴(kuò)展的一些C++程序庫的總稱2022-11-11Matlab實(shí)現(xiàn)多子圖同步調(diào)整視角
這篇文章主要為大家介紹了如何利用Matlab實(shí)現(xiàn)多子圖同步調(diào)整視角,文中的示例代碼講解詳細(xì),對我們學(xué)習(xí)Matlab有一定幫助,需要的可以參考一下2022-03-03Opencv學(xué)習(xí)教程之漫水填充算法實(shí)例詳解
這篇文章主要給大家介紹了Opencv學(xué)習(xí)教程之漫水填充算法的相關(guān)資料,文中給出了詳細(xì)的示例代碼供大家參考學(xué)習(xí),對大家具有一定的參考價值,需要的朋友們下面跟著小編一起來學(xué)習(xí)學(xué)習(xí)吧。2017-06-06C++ DLL動態(tài)庫的創(chuàng)建與調(diào)用(類庫,隱式調(diào)用)
本文主要介紹了C++ DLL動態(tài)庫的創(chuàng)建與調(diào)用(類庫,隱式調(diào)用),文中通過示例代碼介紹的非常詳細(xì),具有一定的參考價值,感興趣的小伙伴們可以參考一下2022-05-05QTableWidget設(shè)置只讓某一列可編輯的實(shí)現(xiàn)
本文介紹了如何將QTableWidget的某一列設(shè)置為可編輯,以便用戶可以輸入自定義數(shù)據(jù),文中通過示例代碼介紹的非常詳細(xì),對大家的學(xué)習(xí)或者工作具有一定的參考學(xué)習(xí)價值,需要的朋友們下面隨著小編來一起學(xué)習(xí)學(xué)習(xí)吧2023-08-08