行远-自迩

导航

4. 中值滤波

一、椒盐噪声

void salt(Mat& img, int num)
{
    if (img.data == NULL)
        return;
    srand(time(NULL));
    int i, j;
    for (int k = 0; k < num; k++)
    {
        i = rand() % img.rows;
        j = rand() % img.cols;
        img.at<Vec3b>(i, j)[0] = 255;
        img.at<Vec3b>(i, j)[1] = 255;
        img.at<Vec3b>(i, j)[2] = 255;
    }
}

二、排序

中值滤波原理,用核函数依次扫描每个像素,将核函数覆盖的图像区域像素排序,取出中值。

三、滤波实现

 

 

Mat median_filter(Mat& noise_img)
{
    int height = noise_img.rows;
    int width = noise_img.cols;
    int channel = noise_img.channels();

    // prepare output
    Mat out = Mat::zeros(height, width, noise_img.type());
    int pad = floor(kernel_size / 2);
    uchar kernel_value[kernel_size * kernel_size] = {0};

    for (int y = 0; y < height; y++)
    {
        for (int x = 0; x < width; x++)
        {
            for (int c = 0; c < channel; c++)
            {
                int count = 0;
                // get neighbor pixels
                for (int dy = -pad; dy < pad + 1; dy++)
                {
                    for (int dx = -pad; dx < pad + 1; dx++)
                    {
                        if (((y - pad) > 0) && ((x - pad) > 0)&& ((y + pad) < height) && ((x + pad) < width))
                        {
                            //边界像素pad/2不管,保持原样
                            kernel_value[count++] = (uchar)noise_img.at<Vec3b>(y+dy, x+dx)[c];
                        }
                        else
                        {
                            //kernel_value[count++] = 0;
                            kernel_value[count++] = (uchar)noise_img.at<Vec3b>(y , x )[c];;
                        }
                    }
                }
                sort(kernel_value, kernel_value + count);
                out.at<Vec3b>(y, x)[c] = (uchar)kernel_value[(int)floor(count / 2) + 1];
            }
        }
    }
    return out;
}

 

     

posted on 2020-07-09 11:35  行远-自迩  阅读(371)  评论(0编辑  收藏  举报