如何在 OpenCV 中计算矩阵的直方图?

Posted

技术标签:

【中文标题】如何在 OpenCV 中计算矩阵的直方图?【英文标题】:How to calculate histogram of a matrix in OpenCV? 【发布时间】:2015-10-07 16:51:33 【问题描述】:

我有一个由来自0 to N 的整数组成的矩阵,我想获得一个大小为N+1 的数据矩阵,其中每个元素都有每个数字的出现次数。

所以如果输入矩阵是

0 0 0
1 1 0
0 0 2

那么我的输出应该是

// occurences of  0  1  2
hist           = [6, 2, 1]

在 C++ OpenCV 中是否有一种简单的(内置)方法可以实现这一点,例如 MATLAB 中的 hist 函数?

谢谢!

【问题讨论】:

您正在寻找直方图均衡化?? 不,我只需要直方图本身。 docs.opencv.org/modules/imgproc/doc/histograms.html 【参考方案1】:

只是为了提供 OpenCV calcHist 的替代方案,您可以使用 std::vector,并在灰度值位置递增计数器:

#include <opencv2\opencv.hpp>
#include <iostream>
#include <algorithm>
#include <numeric>
using namespace std;
using namespace cv;

int main(void)

    // Grayscale image
    Mat1b img = imread("path_to_image", IMREAD_GRAYSCALE);

    // Compute histogram
    vector<int> hist(256, 0);
    for (int r = 0; r < img.rows; ++r)
        for (int c = 0; c < img.cols; ++c)
            ++hist[img(r, c)];

    cout << "number of 0: " << hist[0] << endl;
    cout << "number of 1: " << hist[1] << endl;
    // etc...


    // Sort according to frequency

    vector<int> indices(256);
    iota(indices.begin(), indices.end(), 0); // 0, 1, ... 255
    sort(indices.begin(), indices.end(), [&hist](int lhs, int rhs)  return hist[lhs] > hist[rhs]; );

    cout << "1st frequent number: " << indices[0] << " with N: " << hist[indices[0]] << endl;
    cout << "2nd frequent number: " << indices[1] << " with N: " << hist[indices[1]] << endl;
    // etc

    return 0;


更新了 sn-p 以根据频率递减对结果进行排序。

【讨论】:

【参考方案2】:

此代码从图像中读取所有灰度值并产生频繁出现的值(值出现的次数)。即

像素值“0”出现的次数,

像素值 '1' 出现的次数,... 以此类推,直到 256。

#include <opencv\cv.h>
#include <highgui\highgui.hpp>
using namespace std;
using namespace cv;
    int main()

cv::Mat img = cv::imread("5.jpg",0);

//for(int j=0;j<img.rows;j++) 
//
//  for (int i=0;i<img.cols;i++)
//  
//    int a;
//  a=img.at<uchar>(j,i);
//     cout<<a<<endl; 
//  
//
vector<int> values_rgb;
for(int i=0; i<20; i++)

    for(int j=0; j<20; j++)
    
        int value_rgb = img.at<uchar>(i,j);
        values_rgb.push_back(value_rgb);
        //cout << "(" << i << "," << j << ") : " << value_rgb <<endl;
    

// Sorting of values in ascending order 
vector<int> counter_rg_values;
for(int l=0; l<256; l++)


    for(int k=0; k<values_rgb.size(); k++)
    
        if(values_rgb.at(k) == l)
        
            counter_rg_values.push_back(l);
        
    

//for(int m=0;m<counter_rg_values.size();m++)
//cout<<m<<" "<< counter_rg_values[m] <<endl;
int m=0;
for(int n=0;n<256;n++)

    int c=0;
    for(int q=0;q<counter_rg_values.size();q++)
    
        if(n==counter_rg_values[q])
        
            //int c;
        c++;
        m++;
        
    

    cout<<n<<"= "<< c<<endl;

cout<<"Total number of elements "<< m<<endl;

cv::imshow("After",img);
waitKey(0);

上面关于https://***.com/a/32902450/3853072的讨论链接

【讨论】:

你知道你可以用 3 行代码计算直方图吗? 不使用函数 hist???如果是的话,我不知道先生。!先生,我们该怎么办?? @Miki 是的!我明白了,先生。!!谢谢!

以上是关于如何在 OpenCV 中计算矩阵的直方图?的主要内容,如果未能解决你的问题,请参考以下文章

计算机视觉OpenCV中直方图处理函数简述

科普丨计算机视觉OpenCV中直方图处理函数简述

如何使用 OpenCV 实现图像均衡?

使用Python,OpenCV计算图像直方图(cv2.calcHist)

使用Python,Opencv进行二维直方图的计算及绘制

使用OpenCV,Numpy计算直方图,Matplot绘制直方图及分析