//直方图规格化
void SpecifyHistogram(const Mat& src, const Mat& dst, Mat& out) {
assert(src.cols == dst.cols && src.rows == dst.rows);
assert(src.cols == dst.cols && out.rows == out.rows);
//计算直方图
auto src_hist = CalHistgram(src);
auto dst_hist = CalHistgram(dst);
//初始化
vector<vector<double>>src_p(256);
vector<vector<double>>dst_p(256);
vector<vector<double>>map(256);
for (int i = 0; i < src_p.size(); ++i) {
src_p[i].resize(3);
dst_p[i].resize(3);
map[i].resize(3);
}
int total = src.cols * src.rows;
//累积分布
for (int i = 0; i < src_p.size(); ++i) {
for (int j = 0; j < src_p[i].size(); ++j) {
src_p[i][j] = (i == 0 ? 0 : src_p[i - 1][j]) + src_hist[i][j] * 1.0 / total;
dst_p[i][j] = (i == 0 ? 0 : dst_p[i - 1][j]) + dst_hist[i][j] * 1.0 / total;
}
}
//建立映射
for (int k = 0; k < 3; ++k) {
for (int i = 0; i < map.size(); ++i) {
int index = 0;
double min_val = fabs(src_p[i][k] - dst_p[0][k]);
for (int j = 1; j < map.size(); ++j) {
double val = fabs(src_p[i][k] - dst_p[j][k]);
if (min_val > val) {
min_val = val;
index = j;
}
}
map[i][k] = index;
}
}
//规格化
for (int row = 0; row < src.rows; row++)
{
for (int col = 0; col < src.cols; col++)
{
auto vec3b = src.at<Vec3b>(row, col);
auto& out_vec3b = out.at<Vec3b>(row, col);
out_vec3b[0] = saturate_cast<uchar>(map[vec3b[0]][0]);
out_vec3b[1] = saturate_cast<uchar>(map[vec3b[1]][1]);
out_vec3b[2] = saturate_cast<uchar>(map[vec3b[2]][2]);
}
}
}
直方图规格化C++代码实现
最新推荐文章于 2023-03-15 21:29:26 发布