基于Opencv的图像颜色分析(源码)
点击下方卡片,关注“新机器视觉”公众号
视觉/图像重磅干货,第一时间送达
一般来说,直接分析RGB色彩域的颜色分布不是一个好的思路,我们一般转换到HSV域来分析。但是本文只要是应网友提问,实现最基本的RGB色彩域的主颜色分析。
代码分为以下部分:
1、生成测试图片。为了测试算法是否准确,主动生成具有25种不同颜色同比重的图片(每种4%)的测试图片。
////创建具有25种不同颜色同比重的图片Mat src = Mat(250,250,CV_8UC3,Scalar(0));//生成时间种子time_t t;time(&t);RNG rng(t);//创建图片for (int i = 0;i<250;i+=10)rectangle(src,Point(0,i),Point(src.cols,i+9),Scalar(rng.uniform(0,255),rng.uniform(0,255),rng.uniform(0,255)),-1);imshow("src",src);imwrite("e:/template/maincolor.jpg",src);

生成的结果大概是这个样子的。
2、读取图片数据,保存到3维数组中去。
//bgr立方体int *iTable = new int [256,256,256];for (int b=0;b<256;b++){for (int g=0;g<256;g++){for (int r=0;r<256;r++){iTable[b,g,r] = 0;}}}//出现过的颜色vectorcolorAppeared; //读取数据for (int i=0;i{for (int j=0;j{int b = src.at(i,j)[0]; int g = src.at(i,j)[1]; int r = src.at(i,j)[2]; if (iTable[b,g,r] == 0)colorAppeared.push_back(src.at(i,j)); iTable[b,g,r] ++;}}
3、将数组结果保存到vector中,使用标准库的排序方法。需要注意的是这里重载了vector的比较函数
//重载用于排序的比较函数bool Comp(const std::pairint > &a,const std::pairint > &b){return a.second > b.second;}//将出现过的数据插入标准库for (int i=0;i{Vec3b vec3b = colorAppeared[i];int b = vec3b[0];int g = vec3b[1];int r = vec3b[2];std::pairint > apair(vec3b,iTable[b,g,r]);result.push_back(apair);}//进行排序sort(result.begin(),result.end(),Comp);
4、显示最后结果
////显示结果 前20Mat matResult = Mat(200,200,CV_8UC3,Scalar(0));for (int i = 0;i<20;i++){Vec3b vec3b = result[i].first;int iint = result[i].second;float dpercent = (float)iint / (src.rows * src.cols);rectangle(matResult,Point(0,i*10),Point(200,i*10+9),vec3b,-1);printf("第%d种颜色,占比例为%f\n",i+1,(float)dpercent);}imshow("matResult",matResult);

5、完整的代码如下。感谢阅读,希望有所收获,欢迎交流。
using namespace cv;using namespace std;//重载用于排序的比较函数bool Comp(const std::pairint > &a,const std::pairint > &b){return a.second > b.second;}int main( int argc, const char** argv ){////创建具有25种不同颜色同比重的图片Mat src = Mat(250,250,CV_8UC3,Scalar(0));//生成时间种子time_t t;time(&t);RNG rng(t);//创建图片for (int i = 0;i<250;i+=10)rectangle(src,Point(0,i),Point(src.cols,i+9),Scalar(rng.uniform(0,255),rng.uniform(0,255),rng.uniform(0,255)),-1);imshow("src",src);imwrite("e:/template/maincolor.jpg",src);////进行主要颜色分析//用于保存当前出现过的颜色数据结构std::vector<std::pairint >> result;//bgr立方体int *iTable = new int [256,256,256];for (int b=0;b<256;b++){for (int g=0;g<256;g++){for (int r=0;r<256;r++){iTable[b,g,r] = 0;}}}//出现过的颜色vectorcolorAppeared; //读取数据for (int i=0;i{for (int j=0;j{int b = src.at(i,j)[0]; int g = src.at(i,j)[1]; int r = src.at(i,j)[2]; if (iTable[b,g,r] == 0)colorAppeared.push_back(src.at(i,j)); iTable[b,g,r] ++;}}//将出现过的数据插入标准库for (int i=0;i{Vec3b vec3b = colorAppeared[i];int b = vec3b[0];int g = vec3b[1];int r = vec3b[2];std::pairint > apair(vec3b,iTable[b,g,r]);result.push_back(apair);}//进行排序sort(result.begin(),result.end(),Comp);////显示结果 前20Mat matResult = Mat(200,200,CV_8UC3,Scalar(0));for (int i = 0;i<20;i++){Vec3b vec3b = result[i].first;int iint = result[i].second;float dpercent = (float)iint / (src.rows * src.cols);rectangle(matResult,Point(0,i*10),Point(200,i*10+9),vec3b,-1);printf("第%d种颜色,占比例为%f\n",i+1,(float)dpercent);}imshow("matResult",matResult);waitKey();return 0;}
来源:https://www.cnblogs.com/jsxyhelu/p/7008525.html
评论
