【问题标题】:OpenCV behavior differences between Linux and Windows built applicationLinux 和 Windows 构建的应用程序之间的 OpenCV 行为差异
【发布时间】:2017-02-25 04:12:44
【问题描述】:

我有一个在 Windows 中编写和测试的应用程序,它使用 OpenCV 进行图像评估。它使用 OpenCV 3.1.0 并使用 MinGW-W64 5.3.0 编译。

现在,我已经克隆了这个应用程序,并在 Linux 环境中构建和测试了它。我首先在 Raspberry Pi(Raspian Jessie)上完成了它,然后在我的笔记本电脑上完成了它(Ubuntu 16.04,g++ 5.4.0)。我评估了相同的图像并得到了不同的结果。

我要发布太多代码并希望每个人都能整理出来,所以我的基本问题是,有什么我应该特别寻找的吗?现在我正在我的笔记本电脑上的 Ubuntu 上调试它,但是如果有人过去有类似的经验并且知道要立即寻找的东西,它可以节省我一些时间。

谢谢

我应该提到我正在使用的功能:

cv::cvtColor
cv::Blur
cv::Canny
cv::FindContours
cv::fitLine
cv::fitEllipse

【问题讨论】:

    标签: c++ linux opencv g++ mingw-w64


    【解决方案1】:

    我发现差异根本与 OpenCV 无关,而是函数“std::fpclassify”的行为,我正在检查一条线的斜率是否为“NaN”。我将结果与“1024”进行比较,看看它是否是一个有效的正常数字,即枚举“FP_NORMAL”。但是,在 linux 中编译时,“FP_NORMAL”等于 4 而不是 1024!问题已解决。

    【讨论】:

    • 哦,如果你找到了解决方案,那我的回答就没用了……我正在写它,而你发布了你的……我希望你能觉得它很有趣。
    • 不,它很有帮助,而且是在正确的轨道上。最后是平台相关的浮点处理。谢谢
    【解决方案2】:

    从您提供给我们的少量信息中,我可以告诉您 OpenCV 算法和函数是独立于平台的。 OpenCV 文档中提到的唯一内容是:


    可移植性,外部依赖

    形式上,代码必须符合 C++ 98 标准。目前尚不建议在实现级别使用 C++ 11 或 TR1 扩展,并且禁止在外部头文件中使用它。 应该摆脱依赖于编译器或依赖于平台的构造和系统调用,例如:

    • 编译器编译指示
    • 特定关键字,例如__stdcall、__inline、__int64(或 long long)。分别使用 CV_INLINE(或 C++ 代码中的简单内联)、CV_STDCALL(尽量避免使用它)、int64。
    • 编译器扩展,例如用于最小值和最大值的特殊宏、重载宏等。
    • 内联汇编
    • Unix 或 Win32 特定的调用,例如bcopy、readdir、CreateFile、WaitForSingleObject 等。
    • 具体的数据大小而不是 sizeof 的(sizeof(int) 而不是 4),字节顺序((int)"\x1\x2\x3\x4" 是 0x01020304 或 0x04030201 还是什么?) , 简单的字符而不是有符号字符或无符号字符,除了文本字符串。对 unsigned char 使用短格式 uchar,对 signed char 使用 schar。使用预处理器指令处理不可移植的代码。

    来源:here


    尝试查看您的代码中的某些内容是否与平台相关。 在我看来(但这只是一种感觉),可能与 OpenCV Mats 中的数字表示有关。尝试看看是否有某些东西取决于平台 int 大小或 float 大小...

    我能想到的就这些了……

    【讨论】:

      【解决方案3】:

      图像加载可能就是其中一种情况。请尝试匹配 imread 之后的 windows & linux 或 mac 中的像素值。根据机器上安装的不同版本和编解码器,它可能变化不大。这种像素值不匹配可能发生在压缩图像格式(如 jpg、png、tiff 等)。它不应该发生在未压缩格式(如 pgm、bmp 或原始格式)中。请阅读 opencv 文档中的以下几行:

      1/ 该函数通过内容而不是文件扩展名来确定图像的类型。

      2/ 在 Microsoft Windows 操作系统和 MacOSX 上,默认使用随 OpenCV 图像(libjpeg、libpng、libtiff 和 libjasper)提供的编解码器。因此,OpenCV 始终可以读取 JPEG、PNG 和 TIFF。在 MacOSX 上,还有一个使用原生 MacOSX 图像阅读器的选项。但请注意,由于 MacOSX 中嵌入了颜色管理,目前这些原生图像加载器会提供具有不同像素值的图像。

      3/ 在 Linux、BSD 风格和其他类似 Unix 的开源操作系统上,OpenCV 会查找随操作系统映像提供的编解码器。安装相关软件包(不要忘记开发文件,例如,Debian 和 Ubuntu 中的“libjpeg-dev”)以获得编解码器支持或在 CMake 中打开 OPENCV_BUILD_3RDPARTY_LIBS 标志。

      Link

      【讨论】:

      • Thubsup。在 windows 下保存为 PNG 的相同位图与 Linux 相比也存在差异。不仅适用于 MAC。我们只是放弃了将成像结果与 PNG 格式的参考图像进行比较的不明智的想法。 :-)
      猜你喜欢
      • 1970-01-01
      • 2010-10-29
      • 1970-01-01
      • 2011-09-29
      • 1970-01-01
      • 2014-12-23
      • 1970-01-01
      • 2010-09-25
      • 2012-09-01
      相关资源
      最近更新 更多