zoukankan      html  css  js  c++  java
  • 3.6.1直方图&最大熵分割

      1 ////////////////////////////////////////////////////////////////////////////////////
      2 ////源码来源于:https://blog.csdn.net/fanhongweifd/article/details/47305823
      3 ///////////////////////////////////////////////////////////////////////////////////
      4 #include <opencv2opencv.hpp>
      5 #include<opencv2imgprocimgproc.hpp>
      6 #include <iostream>
      7 #include <string>
      8 #include <windows.h>
      9 //#include "Plate.h"
     10 #include <stdlib.h>
     11 #include <ctime>
     12 #define window_name "均衡化后直接二值化,呵呵"
     13 
     14 using namespace cv;
     15 using namespace std;
     16 
     17 //typedef enum { back, object } entropy_state;
     18 float total;
     19 //绘制hist;  
     20 Mat drawHist(Mat hist, int bins, int height, Scalar rgb)
     21 {
     22     double maxVal = 0;
     23     minMaxLoc(hist, 0, &maxVal, 0, 0);
     24     int scale = 1;
     25     Mat histImg = Mat::zeros(height, bins, CV_8UC3);
     26     float *binVal = hist.ptr<float>(0);
     27     for (int i = 0; i<bins; i++)
     28     {
     29         int intensity = cvRound(binVal[i] * height / maxVal);
     30         rectangle(histImg, Point(i*scale, 0),
     31             Point((i + 1)*scale, (intensity)), rgb, CV_FILLED);
     32     }
     33     //flip(histImg, histImg, 0);
     34     return histImg;
     35 }
     36 //计算直方图;  
     37 Mat Hist(const Mat& src)
     38 {
     39     Mat hist;
     40     int bins = 256;
     41     int histSize[] = { bins };
     42     float range[] = { 0,256 };
     43     const float* ranges[] = { range };
     44     int channels[] = { 0 };
     45     calcHist(&src, 1, channels, Mat(), hist, 1, histSize, ranges, true, false);
     46     Mat histImg = drawHist(hist, bins, 200, Scalar(255, 0, 0));
     47     imshow("histRGB", histImg);
     48     return hist;
     49 }
     50 //计算当前熵;  
     51 float calEntropy(const Mat& hist, int threshold)
     52 {
     53     float total_back = 0, total_object = 0;
     54     float entropy_back = 0, entropy_object = 0;
     55     float entropy = 0;
     56     int i = 0;
     57     const float* hist_p = (float*)hist.ptr<float>(0);
     58     total = 0;
     59     for (i = 0; i<hist.cols; i++)  //total是总的点数
     60     {
     61         total += hist_p[i];
     62     }
     63     for (i = 0; i<threshold; i++)
     64     {
     65         total_back += hist_p[i];
     66     }
     67     total_object = total - total_back;
     68 
     69     //背景熵;  
     70     for (i = 0; i<threshold; i++)
     71     {
     72         //      if(hist_p[i]==0)  
     73         //          continue;  
     74         float percentage = hist_p[i] / total_back;
     75         if (percentage >0)
     76         {
     77             entropy_back += -percentage * logf(percentage); // 能量的定义公式 
     78         }
     79     }
     80     //前景熵;  
     81     for (i = threshold; i<hist.cols; i++)
     82     {
     83         //      if(hist_p[i]==0)  
     84         //      {  
     85         //          continue;  
     86         //      }  
     87         float percentage = hist_p[i] / total_object;
     88         if (percentage >0)
     89         {
     90             entropy_object += -percentage * logf(percentage); // 能量的定义公式; 
     91         }
     92     }
     93 
     94     entropy = entropy_object + entropy_back;
     95     //entropy =entropy_object;  
     96     return entropy;
     97 }
     98 
     99 float LeftBackEntropy(const Mat& hist, int threshold)  //这个函数是测试随着阈值不断增加,左侧也就是背景熵的变化
    100 {
    101     float total_back = 0, total_object = 0;
    102     float entropy_back = 0, entropy_object = 0;
    103     float entropy = 0;
    104     int i = 0;
    105     const float* hist_p = (float*)hist.ptr<float>(0);
    106     total = 0;
    107     for (i = 0; i<hist.cols; i++)  //total是总的点数
    108     {
    109         total += hist_p[i];
    110     }
    111     for (i = 0; i<threshold; i++)
    112     {
    113         total_back += hist_p[i];
    114     }
    115     total_object = total - total_back;
    116 
    117     //背景熵;  
    118     for (i = 0; i<threshold; i++)
    119     {
    120         //      if(hist_p[i]==0)  
    121         //          continue;  
    122         float percentage = hist_p[i] / total_back;
    123         if (percentage >0)
    124         {
    125             entropy_back += -percentage * logf(percentage); // 能量的定义公式 
    126         }
    127     }
    128 
    129     entropy = entropy_back;
    130     //entropy =entropy_object;  
    131     return entropy;
    132 }
    133 
    134 
    135 
    136 void MaxEntropy(Mat img, Mat hist)
    137 {
    138     total = sum(hist)[0];
    139     float MaxEntropyValue = 0.0, MaxEntropyThreshold = 0.0;
    140     float tmp;
    141 
    142 
    143     cout << hist.size() << endl;
    144 
    145     for (int i = 0; i<hist.cols; i++)
    146     {
    147         tmp = calEntropy(hist, i);
    148 
    149         if (tmp>MaxEntropyValue)
    150         {
    151             MaxEntropyValue = tmp;
    152             MaxEntropyThreshold = i;
    153         }
    154     }
    155     threshold(img, img, MaxEntropyThreshold, 255, CV_THRESH_BINARY);
    156     imshow("thresholdImg", img);
    157     //imwrite("D:/thresholdImg.png",img);  
    158     cout << MaxEntropyThreshold << endl;
    159     cout << MaxEntropyValue << endl;
    160 }
    161 
    162 void LeftEntropy(Mat img, Mat hist)   //这个函数是测试随着阈值不断增加,左侧也就是背景熵的变化
    163 {
    164 
    165     total = sum(hist)[0];
    166     float MaxEntropyValue = 0.0, MaxEntropyThreshold = 0.0;
    167     float tmp;
    168     Mat SingleHist(hist.size(), CV_32FC1);//测试左边图像的熵值
    169 
    170 
    171     for (int i = 0; i<hist.cols; i++)
    172     {
    173         tmp = LeftBackEntropy(hist, i);
    174         SingleHist.at<float>(0, i) = tmp;//这是测试左边图像的熵值
    175 
    176     }
    177 
    178     Mat histImg = drawHist(SingleHist, 256, 200, Scalar(255, 0, 0));
    179     imshow("SingleHist", histImg);
    180 
    181 }
    182 
    183 int main(int argc, char *argv[])
    184 {
    185     //Mat img = imread("smallpicture.jpg");
    186     //Mat src = imread("smallpicture.jpg", 0);
    187     Mat src = imread("D:\液晶屏数字.jpg", 0);
    188     imshow("SRC", src);
    189     Mat src_t = Hist(src);//(256, 1)
    190     Mat hist = Hist(src).t();//(1, 256)
    191     MaxEntropy(src, hist);
    192     LeftEntropy(src, hist);
    193     /*
    194     cout<<hist.size()<<endl;
    195     const float* hist_p = (float*) hist.ptr<float>(0);
    196     int threshold=50;
    197     float total_back=0,total_object=0;
    198     float entropy_back=0,entropy_object=0;
    199     float entropy = 0;
    200     int i=0;
    201     //const float* hist_p = (float*) hist.ptr<float>(0);
    202     total=0;
    203     for (i=0; i<hist.cols; i++)  //total是总的点数
    204     {
    205     total+=hist_p[i];
    206     }
    207     for (i=0; i<threshold; i++)
    208     {
    209     total_back += hist_p[i];
    210     }
    211     total_object=total-total_back;
    212 
    213     //背景熵;
    214     for (i=0; i<threshold; i++)
    215     {
    216     //      if(hist_p[i]==0)
    217     //          continue;
    218     float percentage = hist_p[i]/total_back;
    219     if(percentage>0)
    220     {
    221     entropy_back += -percentage * logf(percentage); // 能量的定义公式
    222     }
    223     }
    224     //前景熵;
    225     for (i=threshold; i<hist.cols; i++)
    226     {
    227     //      if(hist_p[i]==0)
    228     //      {
    229     //          continue;
    230     //      }
    231     float percentage = hist_p[i]/total_object;
    232     if(percentage>0)
    233     {
    234     entropy_object += -percentage * logf(percentage); // 能量的定义公式;
    235     }
    236     }
    237 
    238     entropy = entropy_object+entropy_back;
    239     float percentage = hist_p[0]/total_back;
    240     if(percentage)
    241     {
    242     entropy_back = -percentage * logf(percentage); // 能量的定义公式
    243     cout<<entropy_back<<endl;
    244     }
    245     cout<<total_object<<"  "<<total_back<<"  "<<total<<endl;
    246     cout<<entropy<<endl;
    247     /*
    248     int i;
    249     for(i=0;i<50;i++)
    250     {
    251     cout<<hist_p[i]<< "  ";
    252     }
    253     for(i=0;i++;i<50)
    254     {
    255     cout<<endl;
    256     float sum=calEntropy(hist,50);
    257     cout<<sum<<"  "<<endl;
    258     }
    259     */
    260 
    261 
    262     waitKey();
    263     return 1;
    264 
    265 }
    View Code

    运行效果:

  • 相关阅读:
    kvm
    docker及lvs负载
    zookeeper,及k8s基础概念
    zabbix-proxy及ELK
    gitlab及jenkins
    绘图 Matplotlib Numpy Pandas
    Elasticsearch
    Git命令小结
    win黑窗口命令
    Linux基础命令
  • 原文地址:https://www.cnblogs.com/thebreakofdawn/p/9443766.html
Copyright © 2011-2022 走看看