接上篇:
信息熵
我还尝试了使用信息熵的方式:
图像也可以采用信息熵的方式来计算图像中的信息多少。
- 基本概念:图像信息熵是一种特征的统计形式,反映了图像中平均信息量的多少。它表示图像灰度分布的聚集特征所包含的信息量。图像信息熵通常用来衡量图像的“繁忙”程度或复杂性。较高的熵值通常意味着图像具有更高的细节和复杂度,而较低的熵值则可能表明图像较为简单或模糊。
- 计算方法:图像信息熵可以通过灰度直方图来计算。对于灰度图像,首先计算每个灰度值出现的概率,然后根据这些概率使用公式计算熵。熵的计算公式为:H(x) = ∑ p(i) log2 p(i),其中p(i)是灰度值为i的像素出现的概率。
代码:
double calcImageEntropy(cv::Mat img)
{
if (img.channels() == 3)
{
cv::cvtColor(img, img, cv::COLOR_RGB2GRAY);
}
cv::Mat hist;
int histSize = 256;
float range[] = { 0, 256 };
const float* histRange = { range };
cv::calcHist(&img, 1, 0, cv::Mat(), hist, 1, &histSize, &histRange);
vector<float> p_hist;
float total = 0.0f, total_result = 0.0f;
for (int i = 0; i < histSize; i++)
{
total += hist.at<int>(i, 0);
}
for (int i = 0; i < histSize; i++)
{
float p = hist.at<int>(i, 0) / total;
float logP = 0.0f;
if (p == 0)
{
logP = 0.0f;
}
else
{
logP = log2(p);
}
total_result += p * logP;
}
return total_result;
}
效果不明显。
高斯模糊
有一个思路是,如果一个图像是清晰的,那么抗模糊能力也是相对较强。可以针对图像做两个不同kernel size的高斯模糊,然后两者相减,得到的就是相对清晰的高频分量。谁的分量留的多,谁就更清晰。
代码:
double calcGaussVariance(cv::Mat img)
{
cv::Mat gaussKernel_3, guassKernel_7, divMat, mean, std;
if (img.channels() == 3)
{
cv::cvtColor(img, img, cv::COLOR_RGB2GRAY);
}
cv::GaussianBlur(img, gaussKernel_3, cv::Size(3, 3), 50, 50);
cv::GaussianBlur(img, guassKernel_7, cv::Size(7, 7), 50, 50);
divMat = guassKernel_7 - gaussKernel_3;
cv::meanStdDev(divMat, mean, std);
return std.at<double>(0, 0);
}
代码中的meanStdDev是计算方差的opencv库函数。
经过试验,该方法有效。