You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

CS50 Filter Blur计算结果异常,请求排查代码问题

图像模糊函数错误分析与修复

测试报错情况

  • ❌ 中间像素模糊结果错误
    预期输出:127 140 149,实际输出:145 160 169
  • ❌ 边缘像素模糊结果错误
    预期输出:80 95 105,实际输出:90 106 116
  • ✅ 角落像素模糊结果正确
  • ❌ 3x3图像整体模糊结果错误
    预期输出:70 85 95\n80 9...,实际输出:70 85 95\n90 1...
  • ❌ 4x4图像整体模糊结果错误
    预期输出:70 85 95\n80 9...,实际输出:70 85 95\n90 1...

原始代码

void blur(int height, int width, RGBTRIPLE image[height][width])
{
    for (int i = 0; i < height; i++)
    {
        for (int j = 0; j < width; j++)
        {
            double red = 0,green = 0,blue = 0;
            int count = 0;

            for (int m = 0; m < 3; m++)
            {
                int h = i+m-1;
                for (int n = 0; n < 3; n++)
                {
                    int w = j+n-1;
                    if(h > -1 && w > -1 && h < height && w < width)
                    {
                    red += image[h][w].rgbtRed;
                    green += image[h][w].rgbtGreen;
                    blue += image[h][w].rgbtBlue;
                    count++;
                    }
                }
            }
            red = 1.00*red/count;
            green = 1.00*green/count;
            blue = 1.00*blue/count;
            image[i][j].rgbtRed = round(red);
            image[i][j].rgbtGreen = round(green);
            image[i][j].rgbtBlue = round(blue);
        }
    }
    return;
}

错误原因

核心问题是你在修改原图像像素的同时,后续计算会用到已经被模糊处理过的像素值,而非原始图像的像素数据。

比如处理左上角像素后,当计算它右侧或下方的像素时,读取到的已经是经过模糊后的新值,而非原始值。这种叠加修改会导致计算出的平均值偏高,最终所有非角落的像素结果都不符合预期。

修复方案

先创建原始图像的完整副本,所有模糊计算基于副本的原始数据,修改操作直接作用于原图像。

修复后的代码

void blur(int height, int width, RGBTRIPLE image[height][width])
{
    // 创建原始图像的副本,保存所有原始像素值
    RGBTRIPLE copy[height][width];
    for (int i = 0; i < height; i++)
    {
        for (int j = 0; j < width; j++)
        {
            copy[i][j] = image[i][j];
        }
    }

    for (int i = 0; i < height; i++)
    {
        for (int j = 0; j < width; j++)
        {
            double red = 0, green = 0, blue = 0;
            int count = 0;

            for (int m = 0; m < 3; m++)
            {
                int h = i + m - 1;
                for (int n = 0; n < 3; n++)
                {
                    int w = j + n - 1;
                    if (h >= 0 && w >= 0 && h < height && w < width)
                    {
                        // 从副本中读取原始像素值进行计算
                        red += copy[h][w].rgbtRed;
                        green += copy[h][w].rgbtGreen;
                        blue += copy[h][w].rgbtBlue;
                        count++;
                    }
                }
            }

            // 计算平均值并赋值给原图像
            image[i][j].rgbtRed = round(red / count);
            image[i][j].rgbtGreen = round(green / count);
            image[i][j].rgbtBlue = round(blue / count);
        }
    }
    return;
}

关键修复点

  1. 新增图像副本copy,完全复刻原始图像的所有像素数据;
  2. 计算模糊值时,从副本copy中读取像素,确保始终使用原始值;
  3. 计算完成后将结果写入原图像image,不影响后续计算的原始数据来源。

内容的提问来源于stack exchange,提问作者Wiwatpon Lertworasirikul

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.08.10 15:30:49