|
|
#include <vector>
|
|
|
#include <iostream>
|
|
|
#include <exception>
|
|
|
#include <opencv2/opencv.hpp>
|
|
|
#include <opencv2/imgcodecs.hpp>
|
|
|
#include <opencv2/imgproc.hpp>
|
|
|
#include <opencv2/videoio.hpp>
|
|
|
#include <opencv2/video.hpp>
|
|
|
#include <opencv2/core/core.hpp>
|
|
|
#include <opencv2/highgui/highgui.hpp>
|
|
|
#include <opencv2/video/background_segm.hpp>
|
|
|
#include <sys/time.h>
|
|
|
#include "ImageDetectConfig.h"
|
|
|
#include "log_manager.h"
|
|
|
|
|
|
|
|
|
using namespace std;
|
|
|
using namespace cv;
|
|
|
|
|
|
// cast 计算出的偏差值,小于1.0表示比较正常,大于1.0表示存在亮度异常;
|
|
|
// 当cast异常时,da大于0表示过亮,da小于0表示过暗。
|
|
|
void detect_brightness(cv::Mat input_img, float& cast, float& da)
|
|
|
{
|
|
|
cv::Mat gray_img;
|
|
|
cv::cvtColor(input_img, gray_img, COLOR_BGR2GRAY);
|
|
|
|
|
|
float a = 0, Ma = 0;
|
|
|
int hist[256] = { 0 };
|
|
|
|
|
|
for (int i = 0; i < gray_img.rows; i++)
|
|
|
{
|
|
|
for (int j = 0; j < gray_img.cols; j++) {
|
|
|
a += float(gray_img.at<uchar>(i, j) - 128); // 在计算过程中,考虑128为亮度均值点
|
|
|
hist[gray_img.at<uchar>(i, j)]++;
|
|
|
}
|
|
|
}
|
|
|
|
|
|
da = a / float(gray_img.total());
|
|
|
|
|
|
for (int i = 0; i < 256; i++) {
|
|
|
Ma += abs(i - 128 - da) * hist[i];
|
|
|
}
|
|
|
|
|
|
Ma /= float(gray_img.total());
|
|
|
cast = abs(da) / abs(Ma);
|
|
|
}
|
|
|
|
|
|
void detect_saturation(cv::Mat input_img, float& satu)
|
|
|
{
|
|
|
Mat dstImage1;
|
|
|
cvtColor(input_img, dstImage1, COLOR_RGB2HSV);
|
|
|
vector<Mat> channels;
|
|
|
split(dstImage1, channels);//分离HSV
|
|
|
Scalar mean; //均值
|
|
|
Scalar stddev; //标准差
|
|
|
meanStdDev( channels[1], mean, stddev ); //计算均值和标准差
|
|
|
satu = mean.val[0];
|
|
|
}
|
|
|
|
|
|
void detect_graydiff(cv::Mat img, float& CON, float& ASM, float& ENT, float& MEAN)
|
|
|
{
|
|
|
Mat mi;
|
|
|
int row = img.rows;
|
|
|
int col = img.cols;
|
|
|
//CON=i*i*P(I)
|
|
|
//计算i
|
|
|
mi.create(row, col, img.type());
|
|
|
for (int i = 0; i < row-1; i++)
|
|
|
for (int j = 0; j < col; j++)
|
|
|
{
|
|
|
//cout << "BEF" << int(img.ptr<uchar>(i)[j]) << endl;
|
|
|
mi.at<Vec3b>(i, j) = img.at<Vec3b>(i + 1, j) - img.at<Vec3b>(i, j);
|
|
|
//cout << "IMF:" << int(mi.ptr<uchar>(i)[j]) << endl;
|
|
|
}
|
|
|
//计算p(I) 差值的概率
|
|
|
int new_cols = mi.cols;
|
|
|
int new_rows = mi.rows;
|
|
|
int gray[256] = { 0 };
|
|
|
double gray_prob[256] = { 0 };
|
|
|
int num = 0;// 像素的总个数
|
|
|
//统计直方图各个像素灰度值
|
|
|
for (int i = 0; i < mi.rows; i++)
|
|
|
{
|
|
|
uchar *p = mi.ptr<uchar>(i);
|
|
|
for (int j = 0; j < mi.cols; j++)
|
|
|
{
|
|
|
int value = p[j];
|
|
|
gray[value]++;
|
|
|
num++;
|
|
|
}
|
|
|
}
|
|
|
//计算直方图概率分布
|
|
|
for (int i = 0; i < 256; i++)
|
|
|
{
|
|
|
gray_prob[i] = ((double)gray[i] / num);
|
|
|
}
|
|
|
CON = 0.0;
|
|
|
ASM = 0.0;
|
|
|
ENT = 0.0;
|
|
|
MEAN = 0.0;
|
|
|
double v = 1.0/ 255.0;
|
|
|
for (int i = 0; i <= 255; i++)
|
|
|
{
|
|
|
CON += i*i*gray_prob[i];//计算CON
|
|
|
ASM += gray_prob[i] * gray_prob[i];//计算角度方向二阶矩
|
|
|
if (gray_prob[i]!=0)
|
|
|
ENT += (0-gray_prob[i] * log10(gray_prob[i]));//计算熵
|
|
|
MEAN += v*i*gray_prob[i];//计算平均值
|
|
|
}
|
|
|
return;
|
|
|
}
|
|
|
|
|
|
void detect_definition(cv::Mat input_img, float& sb, float& lap, float& dev)
|
|
|
{
|
|
|
Mat imgGray, imgSobel, imgLap, imgDev, meanValueImage;
|
|
|
cvtColor(input_img, imgGray, CV_BGR2GRAY);
|
|
|
Sobel(imgGray, imgSobel, CV_16U, 1, 1);
|
|
|
Laplacian(imgGray, imgLap, CV_16U);
|
|
|
meanStdDev(imgGray,meanValueImage,imgDev);
|
|
|
sb = mean(imgSobel)[0];
|
|
|
lap = mean(imgLap)[0];
|
|
|
dev = mean(imgDev)[0];
|
|
|
}
|
|
|
|
|
|
|
|
|
int main(int argc, char *argv[])
|
|
|
{
|
|
|
Mat img = imread(argv[1]);
|
|
|
float cast, da, satu, CON, ASM, ENT, MEAN, sb, lap, dev;
|
|
|
Mat img_brightness = img.clone();
|
|
|
detect_brightness(img_brightness, cast, da);
|
|
|
Mat img_saturation = img.clone();
|
|
|
detect_saturation(img_saturation, satu);
|
|
|
Mat img_graydiff = img.clone();
|
|
|
detect_graydiff(img_graydiff, CON, ASM, ENT, MEAN);
|
|
|
Mat img_definition = img.clone();
|
|
|
detect_definition(img_definition, sb, lap, dev);
|
|
|
cout<<cast<<"||"<<da<<"||"<<satu<<"||"<<CON<<"||"<<ASM<<"||"<<ENT<<"||"<<MEAN<<"||"<<sb<<"||"<<lap<<"||"<<dev;
|
|
|
return 0;
|
|
|
}
|