博客
关于我
图像灰度变换原理及c++实现——图像反转,对数变换,对比度拉伸,比特平面分层
阅读量:798 次
发布时间:2023-04-15

本文共 3818 字,大约阅读时间需要 12 分钟。

图像处理技术实现与应用

在图像处理领域,技术细节是实现高效算法的关键。以下是基于指针访问像素的技术实现方法,包括图像反转、对数变换、对比度拉伸以及比特平面分层等核心技术。

1. 图像反转(负片变换)

图像反转是一种简单的灰度变换,常用于增强图像中暗色区域的细节。负片变换的实现逻辑如下:

  • 对于每个像素,计算其反转值:dstdata[j] = 255 - srcdata[j]
  • 这种方法适用于灰度图像和彩色图像,通过简单的计算实现高效反转效果。

2. 对数变换

对数变换是一种灰度调节技术,适用于扩展或压缩图像的灰度级。其实现方法有两种:

  • 方法1:基于指针访问像素,使用公式dstdata[j] = c * log(1 + srcdata[j])进行计算。
  • 方法2:利用OpenCV的矩阵运算功能,直接对灰度图像执行对数变换,并进行归一化处理。

3. 对比度拉伸

对比度拉伸是一种灰度拉伸技术,常用于强化图像的动态范围。实现方法通常采用分段线性变换:

  • 将图像分为三段,分别进行线性变换。例如:
    • 当像素值在区间[min, a]时,使用公式c / a * ptr_dst[j]进行拉伸。
    • 当像素值在区间[a, b]时,使用公式(d - c) / (b - a) * ptr_dst[j]进行拉伸。
    • 当像素值在区间[b, max]时,使用公式(max - d) / (max - b) * ptr_dst[j]进行拉伸。

4. 比特平面分层

灰度图像的每个像素值由8个比特组成。比特平面分层的目标是将这些比特分离成独立的矩阵,便于后续处理:

  • 将每个像素值转换为对应的二进制数。
  • 根据指定的比特位置提取对应的二进制信息,并生成单独的比特平面图像。

代码实现示例

以下是基于OpenCV的实现代码,展示了上述技术的应用:

#include 
#include
#include
void Image_inversion(cv::Mat& src, cv::Mat& dst) { int nr = src.rows; int nc = src.cols * src.channels(); src.copyTo(dst); if (src.isContinuous() && dst.isContinuous()) { nr = 1; nc = src.rows * src.cols * src.channels(); } for (int i = 0; i < nr; ++i) { const uchar* srcdata = src.ptr
(i); uchar* dstdata = dst.ptr
(i); for (int j = 0; j < nc; ++j) { dstdata[j] = 255 - srcdata[j]; } }}void LogTransform1(cv::Mat& src, cv::Mat& dst, double c) { int nr = src.rows; int nc = src.cols * src.channels(); src.copyTo(dst); dst.convertTo(dst, CV_64F); if (src.isContinuous() && dst.isContinuous()) { nr = 1; nc = src.rows * src.cols * src.channels(); } for (int i = 0; i < nr; ++i) { const uchar* srcdata = src.ptr
(i); double* dstdata = dst.ptr
(i); for (int j = 0; j < nc; ++j) { dstdata[j] = c * log(1.0 + srcdata[j]); } } cv::normalize(dst, dst, 0, 255, cv::NORM_MINMAX); dst.convertTo(dst, CV_8U);}cv::Mat LogTransform2(cv::Mat& src, double c) { if (src.channels() > 1) { cv::cvtColor(src, src, CV_RGB2GRAY); } cv::Mat dst; src.copyTo(dst); dst.convertTo(dst, CV_64F); dst = dst + 1.0; cv::log(dst, dst); dst = c * dst; cv::normalize(dst, dst, 0, 255, cv::NORM_MINMAX); dst.convertTo(dst, CV_8U); return dst;}void contrast_stretching(cv::Mat& src, cv::Mat& dst, double a, double b, double c, double d) { src.copyTo(dst); dst.convertTo(dst, CV_64F); double min = 0, max = 0; cv::minMaxLoc(dst, &min, &max, 0, 0); int nr = dst.rows; int nc = dst.cols * dst.channels(); if (dst.isContinuous()) { nr = 1; nc = dst.cols * dst.rows * dst.channels(); } for (int i = 0; i < nr; ++i) { double* ptr_dst = dst.ptr
(i); for (int j = 0; j < nc; ++j) { if (min <= ptr_dst[j] < a) { ptr_dst[j] = (c / a) * ptr_dst[j]; } else if (a <= ptr_dst[j] < b) { ptr_dst[j] = ((d - c) / (b - a)) * ptr_dst[j]; } else if (b <= ptr_dst[j] < max) { ptr_dst[j] = ((max - d) / (max - b)) * ptr_dst[j]; } } } dst.convertTo(dst, CV_8U);}void Bitplane_stratification(cv::Mat& src, cv::Mat& B, int num_Bit) { if (src.channels() > 1) { cv::cvtColor(src, src, CV_RGB2GRAY); } B.create(src.size(), src.type()); for (int i = 0; i < src.rows; ++i) { const uchar* ptr_src = src.ptr
(i); uchar* ptr_B = B.ptr
(i); for (int j = 0; j < src.cols; ++j) { int b[8]; num2Binary(ptr_src[j], b); ptr_B[j] = b[num_Bit - 1] * 255; } }}int main() { cv::Mat src = cv::imread("I:\\Learning-and-Practice\\2019Change\\Image process algorithm\\Img\\(2nd_from_top).tif"); if (src.empty()) { return -1; } cv::Mat dst; // Image_inversion(src, dst); // LogTransform1(src, dst, 10); // dst = LogTransform2(src, 10); // contrast_stretching(src, dst, 20, 100, 30, 200); Bitplane_stratification(src, dst, 8); cv::namedWindow("src"); cv::imshow("src", src); cv::namedWindow("dst"); cv::imshow("dst", dst); cv::waitKey(0);}

总结

上述实现展示了图像反转、对数变换、对比度拉伸以及比特平面分层等核心技术的代码实现。这些技术可以根据具体需求灵活配置,用于图像增强和预处理等多种场景。

转载地址:http://vwgfk.baihongyu.com/

你可能感兴趣的文章
MySQL - ERROR 1406
查看>>
mysql - 视图
查看>>
MySQL - 解读MySQL事务与锁机制
查看>>
MTTR、MTBF、MTTF的大白话理解
查看>>
mt_rand
查看>>
mysql -存储过程
查看>>
mysql /*! 50100 ... */ 条件编译
查看>>
mudbox卸载/完美解决安装失败/如何彻底卸载清除干净mudbox各种残留注册表和文件的方法...
查看>>
mysql 1264_关于mysql 出现 1264 Out of range value for column 错误的解决办法
查看>>
mysql 1593_Linux高可用(HA)之MySQL主从复制中出现1593错误码的低级错误
查看>>
mysql 5.6 修改端口_mysql5.6.24怎么修改端口号
查看>>
MySQL 8.0 恢复孤立文件每表ibd文件
查看>>
MySQL 8.0开始Group by不再排序
查看>>
mysql ansi nulls_SET ANSI_NULLS ON SET QUOTED_IDENTIFIER ON 什么意思
查看>>
multi swiper bug solution
查看>>
MySQL Binlog 日志监听与 Spring 集成实战
查看>>
MySQL binlog三种模式
查看>>
multi-angle cosine and sines
查看>>
Mysql Can't connect to MySQL server
查看>>
mysql case when 乱码_Mysql CASE WHEN 用法
查看>>