c++ - 如何在 openCV 中读取 .tif 浮点灰度图像

标签 c++ opencv c++11 image-processing opencv3.0

我正在尝试读取 OpenCV 中的 .tif.tiff 浮点灰度图像。

我可以读写常规文件格式,如 pngjpg 等,但我无法从我的桌面读取我以前从未使用过的格式 .tif.tiff 格式。

图像:我尝试读取的图像具有以下参数: 尺寸:

size image

以及宽度和高度:

widthHeight image

在一些文档和各种资源之后,我能够理解可以使用 convertTo 函数在可用数据类型之间进行转换,源可以找到 here .然而这并没有很好地工作,我实际上有一个编译错误说:

OpenCV(3.4.1) Error: Assertion failed (size.width>0 && size.height>0) in imshow, file /home/to/opencv/modules/highgui/src/window.cpp, line 356 terminate called after throwing an instance of cv::Exception what(): OpenCV(3.4.1) /home/to/opencv/modules/highgui/src/window.cpp:356: error: (-215) size.width>0 && size.height>0 in function imshow

我使用的代码如下:

#include <opencv2/core.hpp>
#include <opencv2/imgcodecs.hpp>
#include <opencv2/highgui.hpp>
#include <iostream>
#include <string>
using namespace cv;
using namespace std;

int main( int argc, char** argv )
{
    Mat img = imread("/home/to/Desktop/example.tif");
    cv::imshow("source",img);
    Mat dst;  // destination image

    // check if we have RGB or grayscale image
    if (img.channels() == 3) {
        // convert 3-channel (RGB) 8-bit uchar image to 32 bit float
        img.convertTo(dst, CV_32FC3);
    }
    else if (img.channels() == 1) {
        // convert 1-chanel (grayscale) 8-bit uchar image to 32 bit float
        img.convertTo(dst, CV_32FC1);
    }

    // display output, note that to display dst image correctly
    // we have to divide each element of dst by 255 to keep
    // the pixel values in the range [0,1].
    cv::imshow("output",dst/255);
    waitKey();
}

我试图让它工作的其他示例直接来自 OpenCV 文档,可以找到 here , 虽然有一个小的修改。我读自 official documentation选项 IMREAD_ANYCOLOR | IMREAD_ANYDEPTH 也应该被激活,事实上我在下面的第二个附加试验中就是这样做的:

#include <opencv2/core.hpp>
#include <opencv2/imgcodecs.hpp>
#include <opencv2/highgui.hpp>
#include <iostream>
#include <string>
using namespace cv;
using namespace std;

int main( int argc, char** argv )
{
    String imageName( "/home/to/Desktop/example.tif" ); // by default
    if( argc > 1)
    {
        imageName = argv[1];
    }
Mat image;
Mat outImage;
image = imread( imageName, IMREAD_ANYCOLOR | IMREAD_ANYDEPTH ); // Read the file
if( image.empty() )                      // Check for invalid input
{
    cout <<  "Could not open or find the image" << std::endl ;
    return -1;
}
namedWindow( "Display window", WINDOW_AUTOSIZE ); // Create a window for display.

resize(image, outImage, cv::Size(500,500));

imshow("orig", image);
imshow("resized", outImage);



// Show our image inside it.
waitKey(0); // Wait for a keystroke in the window
return 0;

这次编译器运行没有任何错误,但没有显示图像,从下面的打印屏幕可以看出:

image

更新

这是 cv::resize 之后的结果

resized

更新 2

这是应用 imshow("Display window", image*10);

后的结果

5

官方文档中是否有我遗漏的内容或我忘记做的其他事情? 感谢您阐明这个问题。

最佳答案

您的图像由单 channel 64 位 float 组成,范围从 -219.774-22.907。我可以使用 libtiff 附带的 tiffutil 来判断:

tiffutil -verboseinfo  image.tif

TIFFReadDirectory: Warning, Unknown field with tag 33550 (0x830e) encountered.
TIFFReadDirectory: Warning, Unknown field with tag 33922 (0x8482) encountered.
TIFFReadDirectory: Warning, Unknown field with tag 42113 (0xa481) encountered.
Directory at 0x256b3a2
  Image Width: 2277 Image Length: 2153
  Bits/Sample: 64
  Sample Format: IEEE floating point
  Compression Scheme: none
  Photometric Interpretation: "min-is-black"
  Samples/Pixel: 1
  Rows/Strip: 1
  Number of Strips: 2153
  Strips (Offset, ByteCount):
     17466, 18216
     35682, 18216
     53898, 18216
     ...
     ...

我不确定你到底打算做什么,但作为第一次尝试,你可以将 220 添加到每个像素并转换为 unsigned char 并且你的范围将是 0 到 197 这是完美显示:

enter image description here

我实际上是用 Python 做的,因为我用它更快,但 C++ 将遵循完全相同的格式:

import cv2

# Load image
img = cv2.imread('image.tif',cv2.IMREAD_UNCHANGED)

# Add 220 to all values, round to unsigned 8-bit and display
Image.fromarray((img+220).astype(np.uint8)).show()

关于c++ - 如何在 openCV 中读取 .tif 浮点灰度图像,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/56859570/

相关文章:

python - 使用 Python 转换 OpenCV triangulatePoints 输出以用于 perspectiveTransform

c++ - 继承只是为了共享枚举 - 危险吗?

c++ - 使用 std::function 包装非静态成员函数指针

c++ - xiAPI : Failed to change thread scheduler, 检查实时优先级的用户限制

c++ - 使用 boost::mpl::bool_ 而不是 const bool 的优点

c++ - 禁止隐式 `unsigned` 到 `double` 转换

c++ - 我应该什么时候使用 std::bind?

c++ - boost 正则表达式分词器和换行符

opencv - 如何通过 OpenCV 合并大量正方形图像?

android - OpenCV for android 示例程序显示错误