直方图的绘制主要用到calcHist()函数 计算,normal归一化直方图。
基本思路:
1 分离图像通道RGB;
2 用calcHist计算每一通道的直方图
3 用normalize()来进行直方图的归一化。
4 用inline 画出每个通道的直方图。
#include<opencv2/opencv.hpp>
#include<iostream>
#include<math.h>
using namespace cv;
using namespace std;
int main1()
{
Mat img = imread("1.jpg");
if (img.empty())
{
cout << "could not load....." << endl;
return -1;
}
namedWindow("受损图",CV_WINDOW_AUTOSIZE);
imshow("受损图", img);
vector<Mat>bgr_img;
split(img, bgr_img);
const int channels[1] = { 0 };
const int bins[1] = { 256 };
float hranges[2] = { 0, 255 };
const float* ranges[1] = { hranges };
Mat b_hist, g_hist, r_hist;
calcHist(&bgr_img[0], 1, channels, Mat(), b_hist, 1, bins, ranges);
calcHist(&bgr_img[1], 1, channels, Mat(), g_hist, 1, bins, ranges);
calcHist(&bgr_img[2], 1, channels, Mat(), r_hist, 1, bins, ranges);
int hist_w = 512;
int hist_h = 400;
int bin_w = cvRound((double)hist_w / bins[0]); //返回和括号内部最接近的整数
Mat histimage = Mat::zeros(hist_h, hist_w, CV_8UC3);
normalize(b_hist, b_hist, 0, histimage.rows, NORM_MINMAX, -1, Mat());
normalize(g_hist, g_hist, 0, histimage.rows, NORM_MINMAX, -1, Mat());
normalize(r_hist, r_hist, 0, histimage.rows, NORM_MINMAX, -1, Mat());
for (int i = 1; i < bins[0]; i++)
{
line(histimage, Point(bin_w*(i - 1), hist_h - cvRound(b_hist.at<float>(i - 1))), Point(bin_w*(i), hist_h - cvRound(b_hist.at<float>(i))), Scalar(255, 0, 0), 2, 8, 0);
line(histimage, Point(bin_w*(i - 1), hist_h - cvRound(g_hist.at<float>(i - 1))), Point(bin_w*(i), hist_h - cvRound(g_hist.at<float>(i ))), Scalar(0, 255, 0), 2, 8, 0);
line(histimage, Point(bin_w*(i - 1), hist_h - cvRound(r_hist.at<float>(i - 1))), Point(bin_w*(i), hist_h - cvRound(r_hist.at<float>(i))),Scalar(0,0,250),2,8,0);
}
namedWindow("sdsd",CV_WINDOW_AUTOSIZE);
imshow("sdsd", histimage);
waitKey(0);
system("pause");
}
直方图结果
解释
void calcHist(const Mat* images, int nimages, const int* channels, InputArray mask, OutputArray hist, int dims, const int* histSize, const float** ranges, booluniform=true, bool accumulate=false )
image 输入图像 注意是指针型
nimages 需要计算直方图的图像个数,可以有多个,但是一般只做一个图像的直方图,所以nimages=1;
channels 图像的通道,用一个数组表示,channels[1]={0},表示图像为灰度,一个通道。channels[3]={0,1,2},表示图片为彩色,三个通道。指针型。
mask 一个遮罩图像,用来指明那些像素进行计算,一般设置为Mat(),空图像。
hist 输出图像,
dims 输出图像的维度,灰度为1维,彩色为3维。
histSize 直方图横坐标的范围。
const float** ranges 二维数组,表示横坐标的区间范围。
void normalize(InputArray src,OutputArray dst, double alpha=1, doub lebeta=0, int norm_type=NORM_L2, int dtype=-1, InputArray mask=noArray() )
src 输入数组(图像)
dst 输出数组 (图像)
alpha 输出数组的最小值
lebeta 输出苏组的最大值
norm_type 归一化的方法
NORM_MINMAX 线性归一化 (绝对值的最大值)
NORM_INF:可能是归一化数组的C-范数
NORM_L1 : 归一化数组的L1-范数(绝对值的和)
NORM_L2: 归一化数组的(欧几里德)L2-范数