Home > database >  Python problem with exporting numpy matrix to tiff file using cv2.imshow then reading it
Python problem with exporting numpy matrix to tiff file using cv2.imshow then reading it

Time:11-06

I am trying to export my NumPy matrix to a .tiff file then to read its contents to verify if it worked. Given the following snippet

import numpy as np
import cv2

data = np.array([[-0.1 for _ in range(128)] for _ in range(128)], dtype=np.float32)
cv2.imwrite('temp.tiff', data)
print('tiff file written')

image = cv2.imread('temp.tiff')
print(image)

returns

tiff file written
[ WARN:[email protected]] global /io/opencv/modules/imgcodecs/src/grfmt_tiff.cpp (629) readData OpenCV TIFF: TIFFRGBAImageOK: Sorry, can not handle images with 32-bit samples

So then I lower down the dtype parameter to dtype=np.float16

data = np.array([[-0.1 for _ in range(128)] for _ in range(128)], dtype=np.float16)

but then I get another error...

, line 50, in export_images_to_tiff
    cv2.imwrite('temp.tiff', a)
cv2.error: OpenCV(4.6.0) :-1: error: (-5:Bad argument) in function 'imwrite'
> Overload resolution failed:
>  - img data type = 23 is not supported
>  - Expected Ptr<cv::UMat> for argument 'img'
[1]    24228 abort      python3 main.py

I am honestly going nuts with this feature I'm trying to implement. Is there any alternatives or fix to the above? I read the documentation but that didn't help, and looking online these error codes yield nothing relevant. Do I just assume that the tiff file was successfully written in the first 32-bit pass and call it a day?

CodePudding user response:

cv2.imread() has a second parameter, flags, which specifies how to read the image file. According the the docs, the default value of the flags argument to imread() is this:

IMREAD_COLOR
If set, always convert image to the 3 channel BGR color image.

Source: imread docs, IMREAD_COLOR docs.

By default, OpenCV attempts to coerce a file into 3-channel color. Since you have only a single channel, that's not going to work. However, there is a flag which will work:

image = cv2.imread('temp.tiff', cv2.IMREAD_UNCHANGED)

(Thanks to this answer for pointing me in the right direction.)

CodePudding user response:

@Nick ODell's answer works but alternatively one could simply use

import tifffile as tiff

tiff.imsave('temp.tiff', data)
image = tiff.imread('temp.tiff')

while also worked in my case.

  • Related