简体   繁体   English

CS50 pset4 - 过滤器(不太舒适),棕褐色 function

[英]CS50 pset4 - filter (less comfortable), sepia function

I wrote code for the sepia function of the filter pset.我为过滤器 pset 的棕褐色 function 编写了代码。 The code compiles without any errors but the output image is not entirely sepia.代码编译没有任何错误,但 output 图像并不完全是棕褐色。 However, after I wrote the code in different way it works fine.但是,在我以不同的方式编写代码后,它工作正常。 Can someone explain why this happens?有人可以解释为什么会这样吗?

First code:第一个代码:

void sepia(int height, int width, RGBTRIPLE image[height][width])
{

    for (int i = 0; i < height; i++)
    {
        for (int j = 0; j < width; j++)
        {
            RGBTRIPLE pixel={0,0,0};
            RGBTRIPLE pix = image[i][j];

            pixel.rgbtBlue = round(0.272 * pix.rgbtRed + 0.534 * pix.rgbtGreen + 0.131 * pix.rgbtBlue);
            pixel.rgbtGreen = round(0.349 * pix.rgbtRed + 0.686 * pix.rgbtGreen + 0.168 * pix.rgbtBlue);
            pixel.rgbtRed = round(0.393 * pix.rgbtRed + 0.769 * pix.rgbtGreen + 0.189 * pix.rgbtBlue);

            if(pixel.rgbtBlue > 255)
            {
                pixel.rgbtBlue = 255;
            }
             if(pixel.rgbtGreen > 255)
            {
                pixel.rgbtGreen = 255;
            }

             if(pixel.rgbtRed > 255)
            {
                pixel.rgbtRed = 255;
            }

            image[i][j] = pixel;

        }
    }
    return;
}

first code output image:第一个代码 output 图片:

第一个代码输出图像

Second Code:第二个代码:

void sepia(int height, int width, RGBTRIPLE image[height][width])
{

    for (int i = 0; i < height; i++)
    {
        for (int j = 0; j < width; j++)
        {
            int red = image[i][j].rgbtRed;
            int green = image[i][j].rgbtGreen;
            int blue = image[i][j].rgbtBlue;

            //calculate sepia values
            int sepiaRed = round(.393 * red + .769 * green + .189 * blue);
            if(sepiaRed > 255)
            {
                sepiaRed = 255;
            }

            int sepiaGreen = round(.349 * red + .686 * green + .168 * blue);
            if(sepiaGreen > 255)
            {
                sepiaGreen = 255;
            }

            int sepiaBlue = round(.272 * red + .534 * green + .131 * blue);
            if(sepiaBlue > 255)
            {
                sepiaBlue = 255;
            }

            image[i][j].rgbtRed  = sepiaRed;
            image[i][j].rgbtGreen = sepiaGreen;
            image[i][j].rgbtBlue = sepiaBlue;


        }
    }
    return;
}

Second code output:第二个代码 output:

第二个代码输出图像

The difference between the two versions is that the type in which you compute the new pixel value两个版本之间的区别在于您计算新像素值的类型

In the first version the type is whatever the constituent members of RGBTRIPLE are - which I assume is an unsigned 8-bit integer.在第一个版本中,类型是RGBTRIPLE的组成成员是什么——我假设它是一个无符号的 8 位 integer。

 pixel.rgbtBlue = round(0.272 * pix.rgbtRed + 0.534 * pix.rgbtGreen + 0.131 * pix.rgbtBlue);

In this line (and the equivalents for green and red pixels), the value can exceeded 255 which then gets truncated by assignment to an 8-bit unsigned int on assignment to pixel.rgbtBlue .在这一行(以及绿色和红色像素的等效项)中,该值可以超过255 ,然后在分配给pixel.rgbtBlue时通过分配给 8 位无符号整数来截断该值。

The following clamp to saturation:以下钳位饱和:

    if(pixel.rgbtBlue > 255)
    {
        pixel.rgbtBlue = 255;
    }

Will always excute false, as pixel.rgbtBlue cannot hold a value bigger than 255 .将始终执行 false,因为pixel.rgbtBlue不能保存大于255的值。

In the second version of the code, an int is used, which is larger, and in which truncation does not occur, allowing the clamp-to-255 to work correct.在代码的第二个版本中,使用了一个更大的int ,并且不会发生截断,从而允许 clamp-to-255 正常工作。

As people above already comment, the first one has a truncated value in the if conditions, as the avarage operation is resulting in a number bigger than 255... That's why the filter does not work properly.正如上面的人已经评论的那样,第一个在 if 条件下有一个被截断的值,因为 avarage 操作导致一个大于 255 的数字......这就是过滤器不能正常工作的原因。 I would consider as well less "if/else" on the second one, using perhaps a " Ternary Operator ", for a cleaner code:我会考虑在第二个上少用“if/else”,也许使用“ Ternary Operator ”,以获得更清晰的代码:

        image[i][j].rgbtGreen = (sepiaGreen > 255) ? 255 : sepiaGreen;
        image[i][j].rgbtRed = (sepiaRed > 255) ? 255 : sepiaRed;
        image[i][j].rgbtBlue = (sepiaBlue > 255) ? 255 : sepiaBlue;

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM