Prewitt 滤波器、边缘检测

Prewitt filter, edge detection

我有这段实现 Prewitt 边缘检测的代码。我需要做的是只用一个缓冲区来实现它,也就是说,我不会创建图像的副本,而是编辑原始图像。所以如果我想改变值 78 的像素,我不能把新值,例如100,直到所有周围像素的读取值为 78。Color values of the pixels。我一整天都在尝试弄清楚但做不到,如果有人能给我写一些伪代码,我将不胜感激

void filter_serial_prewitt(int *inBuffer, int *outBuffer, int width, int height){
   for (int i = 1; i < width - 1; i ++) {
     for (int j = 1; j < height - 1; j ++) {
        int Fx = 0;
        int Fy = 0;
        int F = 0;
        for (int m = -1; m <= 1; m++) {
            for (int n = -1; n <= 1; n++) {
                Fx += inBuffer[(j + n) * width + (i + m)] * n;
                Fy += inBuffer[(j + n) * width + (i + m)] * m;
            }
        }
            F = abs(Fx) + abs(Fy);

            if (F < THRESHOLD){
                outBuffer[j * width + i] = 255;
            } else{
                outBuffer[j * width + i] = 0;
            }
       }
   }
}

关于 Prewitt 运算符的一件事是它是可分离的。 See the Wikipedia article 了解详情。

要计算单个输出行,您需要执行以下操作(伪代码):

int* buffer = malloc (sizeof(int) * width);
for (int i = 0; i < width; i++)
{
    // Do the vertical pass of the convolution of the first 3 rows into
    // the buffer.
    buffer [ i ] = vertical_convolve(inBuffer [ i ], vertical_kernel);
}

// Next, do the horizontal convolution of the first row. We need to 
// keep the previous value in a temp buffer while we work
int temp0 = horizontal_convolve(buffer [ 0 ], horizontal_kernel);
for (int i = 1; i < width; i++)
{
    int temp1 = horizontal_convolve(buffer[ i ], horizontal_kernel);
    inBuffer [ i - 1 ] = temp0;
    temp0 = temp1;
}

这需要一个 1 像素高和图像宽度的缓冲区。

要处理整个图像,您需要保留上述缓冲区中的 2 个,并且在第三行计算一个像素后,您可以将图像第一行的第一个像素替换为第一个像素第一个缓冲区。然后您可以将新计算的值放入缓冲区。

所以在这种情况下,您不会保留整个第二张图像,而是需要保留大约 2 个 1 像素高且与图像一样宽的缓冲区。