jquave 发表于 2022-1-5 10:10

图像处理 —— 平滑处理


图像噪声:在图像获取、传输过程中收到干扰,而产生的错误的信号。噪声干扰一般是随机产生的。该像素的灰度呈现与邻近像素显著不同的特点。
图像去噪:过滤(去掉)噪音信号,而保持有用的图像信号。根据用户的需求,提高图像的质量。


平滑处理的目的:
(1)模糊图像。提取较大目标前,先去掉太小的细节,或者将目标内的小间断连接起来。
(2)消除噪声。改善图像质量,降低干扰,消除图像中的随机噪声,起到平滑作用。
<hr/>领域处理方法:通过某个模板(滤波器、核)对每个像素与周边相邻像素进行某种数学运算,使该像素上的灰度值获得一个新的灰度值。模板运算也就是卷积运算。图像目标像素点领域中的每个像素分别与模板中的每个元素相乘,求和结果即为中心像素的新值。
备注:本章介绍的平滑处理方式属于空间域法中的局部运算方式。
图像增强可分为空间域法和频域法。
a)空间域法:直接在原图像中像素的灰度值进行处理。有点运算和局部运算两种方式。
b)频域法:在图像的变换域上进行处理,增强感兴趣的频率分量,进行反变换,得到增强后的图像。

<hr/>


(1)二值图像的黑白点噪声消除法
可用模板对目标像素进行卷积求和,求灰度值。计算所得到的值与该点原有像素值进行对比,若大于阈值,则把该点颜色反转。即将卷积计算的加权平均像素值赋给该点像素值。
下面以8连接法为例,使用上述右式,实现该去噪。源码如下:
void HeiBaiPoint()
{
        int nAverage1, nAverage2, nAverage3;
        BYTE *p_data;
        int nWide, nHeight;
        p_data = this->GetData();
        if (m_pBitmapInfoHeader->biBitCount < 9)
        {
                nWide = this->GetWidth();
                nHeight = this->GetHeight();
                Binarization(100); // 二值化
                BYTE* p_temp = new BYTE;
                memcpy(p_temp,m_pData, nWide*nHeight);
                for (int j = 1; j < nHeight -1; j++)
                {
                        for (int i = 1; i < nWide -1; i++)
                        {
                                nAverage1 = 0;
                                nAverage1 = (*(p_data + (j-1)*nWide + i-1) + *(p_data + (j-1)*nWide + i) + *(p_data + (j-1)*nWide + i+1)
                                        + *(p_data + j*nWide + i-1) + *(p_data + j*nWide + i+1)
                                        + *(p_data + (j+1)*nWide + i-1) + *(p_data + (j+1)*nWide + i) + *(p_data + (j+1)*nWide + i+1));
                                nAverage1 = (int)(nAverage1/8);
                                if (abs(nAverage1 - *(p_temp+j*nWide+i)) > 127.5)
                                        *(p_temp+j*nWide+i) = nAverage1;
                        }
                }

                memcpy(p_data, p_temp, nWide*nHeight);
                delete p_temp;
        }
        else
        {
                int averg,averg2,averg3;
                BYTE *p_data;                //原图数据区指针
                int wide,height;    //原图长、宽
                wide=this->GetWidth();//取得原图的数据区宽
                height=this->GetHeight ();//取得原图的数据区高
                Binarization(100);//进行二值化
                BYTE* p_temp=new BYTE;// 申请并分配中间缓存
                memcpy(p_temp,m_pData,wide*height*3);// 复制图象数据到中间缓存
                //用3*3屏蔽窗口的8近邻均值进行滤波
                for(int j=1;j<height-1;j++)
                {       
                        for(int i=1;i<wide-1;i++)
                        {
                                averg=0;
                                averg2=0;
                                averg3=0;
                                //求周围8近邻均值
                                averg=(int)((p_data[(j-1)*wide*3+(i-1)*3]+p_data[(j-1)*wide*3+i*3]
                                +p_data[(j-1)*wide*3+(i+1)*3]+p_data
                                +p_data+p_data[(j+1)*wide*3+(i-1)*3]
                                +p_data[(j+1)*wide*3+i*3]+p_data[(j+1)*wide*3+(i+1)*3])/8);
                                averg2=(int)((p_data[(j-1)*wide*3+(i-1)*3+1]+p_data[(j-1)*wide*3+i*3+1]
                                +p_data[(j-1)*wide*3+(i+1)*3+1]+p_data
                                +p_data+p_data[(j+1)*wide*3+(i-1)*3+1]
                                +p_data[(j+1)*wide*3+i*3+1]+p_data[(j+1)*wide*3+(i+1)*3+1])/8);
                                averg3=(int)((p_data[(j-1)*wide*3+(i-1)*3+2]+p_data[(j-1)*wide*3+i*3+2]
                                +p_data[(j-1)*wide*3+(i+1)*3+2]+p_data
                                +p_data+p_data[(j+1)*wide*3+(i-1)*3+2]
                                +p_data[(j+1)*wide*3+i*3+2]+p_data[(j+1)*wide*3+(i+1)*3+2])/8);
                                if(abs(averg-p_temp)>127.5)
                                        p_temp=averg;
                                if(abs(averg2-p_temp)>127.5)
                                        p_temp=averg2;
                                if(abs(averg3-p_temp)>127.5)
                                        p_temp=averg3;
                        }
                }
                memcpy(p_data,p_temp,wide*height*3);
                delete p_temp;
        }
        return;
}

https://www.zhihu.com/video/1436495409040134144


(2)二值图像中的消除孤立黑像素点
该方法指的是在二值图像中,消除孤立于周围的黑像素点。在某个黑像素点领域像素都为白的情况下,将该像素置为白。
下面以8连接法为例,使用上述左式,实现该去噪。源码如下:
void OutAlonePoint()
{
        BYTE *p_data;
        p_data = this->GetData();
        int nWide, nHeight;
        Binarization(100); // 将图像二值化
        if (m_pBitmapInfoHeader->biBitCount < 9)
        {
                nWide = this->GetWidth();
                nHeight = this->GetHeight();
                BYTE* p_temp = new BYTE;
                memcpy(p_temp, m_pData, nWide*nHeight);

                for (int j = 1; j < nHeight-1; j++)
                {
                        for (int i = 1; i < nWide -1; i++)
                        {
                                if (*(p_temp + nWide*j + i) == 255)
                                        continue;
                                if (*(p_temp+nWide*(j-1)+i) + *(p_temp+nWide*j+i-1)
                                        + *(p_temp+nWide*j +i+1) + *(p_temp+nWide*(j+1)+i) == 4*255)
                                {
                                        *(p_data + nWide*j + i) = 255;
                                }
                        }
                }

                delete p_temp;
        }
}

https://www.zhihu.com/video/1436496716904583168


本文参考:
页: [1]
查看完整版本: 图像处理 —— 平滑处理