0

I am working with OpenCV in Python. I found that working with uint8 and float32 works in OpenCV 4. This question OpenCV Mat element types and their sizes shows some more data types but I got an error when choosing e.g. 64bit float.

If I simply create a array of integers e.g.:

img1 = np.array([[[5, 255, 20], [4, 9, 85]],
         [[6, 12, 150], [14, 8, 0]]
])

and try to convert BGR to RGB with img2 = cv2.cvtColor(img1, cv2.COLOR_BGR2RGB) , I get an error:

 OpenCV(4.6.0) d:\a\opencv-python\opencv-python\opencv\modules\imgproc\src\color.simd_helpers.hpp:94: error: (-2:Unspecified error) in function '__cdecl cv::impl::`anonymous-namespace'::CvtHelper<struct cv::impl::`anonymous namespace'::Set<3,4,-1>,struct cv::impl::A0xf2302844::Set<3,4,-1>,struct cv::impl::A0xf2302844::Set<0,2,5>,2>::CvtHelper(const class cv::_InputArray &,const class cv::_OutputArray &,int)'
> Unsupported depth of input image:
>     'VDepth::contains(depth)'
> where
>     'depth' is 4 (CV_32S)

If I read a PNG image and e.g. divide it by 2 and get decimal numbers, the error I get when trying to apply the same function is:

OpenCV(4.6.0) d:\a\opencv-python\opencv-python\opencv\modules\imgproc\src\color.simd_helpers.hpp:94: error: (-2:Unspecified error) in function '__cdecl cv::impl::`anonymous-namespace'::CvtHelper<struct cv::impl::`anonymous namespace'::Set<3,4,-1>,struct cv::impl::A0xf2302844::Set<3,4,-1>,struct cv::impl::A0xf2302844::Set<0,2,5>,2>::CvtHelper(const class cv::_InputArray &,const class cv::_OutputArray &,int)'
> Unsupported depth of input image:
>     'VDepth::contains(depth)'
> where
>     'depth' is 6 (CV_64F)

My questions are:

  1. Are the uint8 and float32 the only data types that work in OpenCV?
  2. Are the uint8 and float32 the only data types that work in OpenCV for 3-channel representation (RGB/BGR) and grayscale?
  3. If the answer is yes, why are those data types the ones that are necessary? I understand why uint8 could be necessary, since a 3 channel image and values 0-255 is represented with 8 bits (2^8). But why float32 and why others not?
Judita
  • 13
  • 4
  • 1
    opencv can, without any problem, work with 64 bit float pixel/channel data (e.g. CV_64FC1 and CV_64FC3) and many other types, but I don't know whether this is also possible in python. And some (image processing) functions are not supporting every kind of data. – Micka Aug 22 '22 at 15:27
  • Can you show the full error message, I would like to know which function is affected and where this VDepth is coming from. – Micka Aug 22 '22 at 15:29
  • 2
    Each function in OpenCV has a specific set of data types it supports. It seems that the color space conversion function you use does not support 32 bit ints or 64 bit floats. In general, there is little reason to use 64 bit floats in image processing, single-precision is usually more than enough, and it saves a lot of memory. OpenCV is more focused on speed than on precision, so mostly it is used with 8 bit ints. – Cris Luengo Aug 22 '22 at 15:37
  • @Micka I edited the post to show the full error message and which function the error is coming from. – Judita Aug 23 '22 at 06:59
  • @CrisLuengo does this mean that we can safely assume that limiting input image to only float32 and uint8 would be good enough even for other features on that image like edge detection, camera pose estimation, feature detection etc.? – Judita Aug 23 '22 at 07:00
  • simd_helpers sounds like SIMD registers, which could be limited to 32 bit float. Can you show your opencv getBuildEnvironment? Is it using SSE only (instead of SSE2)? See https://en.wikipedia.org/wiki/Streaming_SIMD_Extensions – Micka Aug 23 '22 at 07:33
  • 1
    [doesn't matter. there is simply no implementation for double floats](https://github.com/opencv/opencv/blob/17234f82d025e3bbfbf611089637e5aa2038e7b8/modules/imgproc/src/color_rgb.dispatch.cpp#L550) just convert using `.astype(np.float32)` before – Christoph Rackwitz Aug 23 '22 at 07:49
  • This is the getBuildEnvironment: Baseline: SSE SSE2 SSE3 requested: SSE3 Dispatched code generation: SSE4_1 SSE4_2 FP16 AVX AVX2 requested: SSE4_1 SSE4_2 AVX FP16 AVX2 AVX512_SKX SSE4_1 (16 files): + SSSE3 SSE4_1 SSE4_2 (1 files): + SSSE3 SSE4_1 POPCNT SSE4_2 FP16 (0 files): + SSSE3 SSE4_1 POPCNT SSE4_2 FP16 AVX AVX (4 files): + SSSE3 SSE4_1 POPCNT SSE4_2 AVX AVX2 (31 files): + SSSE3 SSE4_1 POPCNT SSE4_2 FP16 FMA3 AVX AVX2 – Judita Aug 23 '22 at 08:26
  • “limiting input image to only float32 and uint8 would be good enough even for other features […]?” I don’t know OpenCV well enough to guarantee that, some functionality might be available only for integer-valued images. The documentation for each function should list which data types are supported by that function. See for example [cvtColor](https://docs.opencv.org/4.6.0/d8/d01/group__imgproc__color__conversions.html#ga397ae87e1288a81d2363b61574eb8cab): “input image: 8-bit unsigned, 16-bit unsigned (CV_16UC...), or single-precision floating-point.”. – Cris Luengo Aug 23 '22 at 14:59

0 Answers0