更快的图像镜像算法

Faster image mirroring algorithm

本文关键字:镜像 算法 图像      更新时间:2023-10-16

我已经知道如何垂直或水平翻转图像。我有以下水平执行此操作的代码。这里的图像数据存储在QImage中,就像我在这里使用Qt一样。

QImage image(imageFileName);
QImage newImage(image);
if(image.depth() > 8)
{
    for (int idx_Y = 0; idx_Y < image.height(); idx_Y++)
    {
        for (int idx_X = 0; idx_X < image.width(); idx_X++)
        {
            QRgb rgb = image.pixel(image.width() - 1 - idx_X, idx_Y);
            newImage.setPixel(idx_X, idx_Y, rgb);
        }
    }
}

我相信有更快的方法可以完成它。但是,我不希望堆上有任何内存分配。你能告诉我还有什么其他更快的算法吗?

谢谢。

详细说明@Spektres提示

2 嵌套的循环不是问题...setPixel 和 Pixel 函数通常在大多数 gfx API 上爬行。使用直接像素访问通常会提高速度~1000倍或更多...

这可能看起来像:

QImage image(imageFileName);
QImage newImage(image);
if (image.depth() >= 8) {
  const int bytesPerPixel = image.depth() / 8;
  for (int y = 0; y < image.height(); ++y) {
    char *dataSrc = image.bits() + y * image.bytesPerLine();
    char *dataDst = newImage.bits() + y * newImage.bytesPerLine()
      + (newImage.width() - 1) * bytesPerPixel;
    for (int i = image.width(); i--;
      dataSrc += bytesPerPixel, dataDst -= bytesPerPixel) {
      for (int i = 0; i < bytesPerPixel; ++i) dataDst[i] = dataSrc[i];
    }
  }
}

请注意,我image.depth() > 8更改为image.depth() >= 8.(我认为没有理由排除例如 QImage::Format_Grayscale8 .(

用于就地镜像QImage newImage的略微修改的版本(考虑到它已经被复制(:

QImage image(imageFileName);
QImage newImage(image);
if (newImage.depth() >= 8) {
  const int bytesPerPixel = newImage.depth() / 8;
  for (int y = 0; y < image.height(); ++y) {
    char *dataL = newImage.bits() + y * newImage.bytesPerLine();
    char *dataR = dataL + (newImage.width() - 1) * bytesPerPixel;
    for (; dataL < dataR; dataL += bytesPerPixel, dataR -= bytesPerPixel) {
      for (int i = 0; i < bytesPerPixel; ++i) std::swap(dataL[i], dataR[i]);
    }
  }
}

关于QImageqRgb(),您可能还会注意到Qt支持每个组件16位的QImage s(从Qt 5.12开始(。


我在SO:将像素值设置为 16 位灰度 QImage
这可能也很有趣。