0

我正在尝试创建一个循环,我可以在其中执行以下操作:-

x x x y y y y y
x x x y y y y y
x x x y y y y y
y y y y y y y y 
y y y y y y y y 

(顺便说一下,上面是一个 8x5 的网格。)

  1. 获取所有标记为 x 的值
  2. 将所有 9 个 x 值相加
  3. 用我刚刚找到的总和值替换 x 值
  4. 然后将所有 x 值乘以 1/9
  5. 然后移动到下一个 x 值块,如下所示:-
y y y x x x y y
y y y x x x y y
y y y x x x y y
y y y y y y y y 
y y y y y y y y 

我试过这样做: -

for(int j=0;j<image.rows;j++)
{
    for (int i=0;i<image.cols;i++)
    {
        for (int y=0; y < 9; y++) {
            sum = image.at<uchar>(j,i) + sum;
            change = sum/9;
        }
        image.at<uchar>(j,i) = change;
    }
}

但它只是行不通。

4

4 回答 4

2

您正在逐个像素地迭代图像,但为了执行您想要的操作,您需要按 3x3 像素组进行迭代:

for(int j = 0; j < image.rows; j += 3)
{
    for (int i = 0; i < image.cols; i += 3)
    { 
        uchar sum = 0;
        for(int x = 0; x < 3; ++x) {
            for(int y = 0; y < 3; ++y) {
                sum += image.at<uchar>(j + x,i + y);
            }
        }
        sum  /= 9;

        for(int x = 0; x < 3; ++x) {
            for(int y = 0; y < 3; ++y) {
                image.at<uchar>(j + x,i + y) = sum ;
            }
        }
    }
}

您还需要处理图像尺寸不是 3 的倍数的情况。

于 2013-11-06T08:18:52.743 回答
2

@zakinster 已经为您提供了一个很好的解决方案,但我建议您使用 OpenCV 的功能来执行计算平均值或设置值等操作,而不是使用循环。这将创建更短且更具可读性的解决方案。此外,您必须确保该算法在图像不是 3 的倍数时有效。这种情况下通常的 C++ 技巧是使用 (x/3*3) 而不是 x。

代码应如下所示:

for(int j=0; j<image.rows/3*3; j+=3)
    for(int i=0; i<image.cols/3*3; i+=3)
    {
        Mat tmp(image,Rect(i,j,3,3));
        tmp.setTo(mean(tmp));
    }

相同代码的更短但可读性更低的版本:

for(int j=0; j<image.rows/3*3; j+=3)
    for(int i=0; i<image.cols/3*3; i+=3)
        image(Rect(i,j,3,3)).setTo(mean(image(Rect(i,j,3,3))));
于 2013-11-06T09:30:57.597 回答
1
    change = sum*(1/9);

1/9 是整数除法,所以结果为零。改为使用change = sum/9.0

于 2013-11-06T08:15:06.633 回答
0

您的代码的问题是您对变量 y 的内部循环永远不会改变值 i 或 j。所以,第一次进入这个循环时,你只需将图像中 (0, 0) 处的值乘以 9,然后除以 9。

您将不得不找出一种方法来根据 y 对 i 和 j 执行转换,可能通过编辑此行:

sum = image.at<uchar>(j, i) + sum;

这样它就可以处理标有 x 的单元格。

然后,您将需要修改在外部循环中更新 i 和 j 的方式。看起来您需要将 j 增加 3 才能跳过刚刚处理的块。

这将涉及一些想法,您需要考虑如何处理网格尺寸不是三的倍数的情况,但我会首先让内部循环工作。

于 2013-11-06T08:20:37.170 回答