How to find out what type of a Mat object is with Mat::type() in OpenCV?

OpencvOpencv Mat

Opencv Problem Overview


I am kind of confused with type() method of Mat object in OpenCV.
If I have following lines:

mat = imread("C:\someimage.jpg");
type = mat.type();

and type = 16, how do I find out what type of mat matrix is?.
I tried to find the answer in its manual and in a couple of books in vain.

Opencv Solutions


Solution 1 - Opencv

Here is a handy function you can use to help with identifying your opencv matrices at runtime. I find it useful for debugging, at least.

string type2str(int type) {
  string r;

  uchar depth = type & CV_MAT_DEPTH_MASK;
  uchar chans = 1 + (type >> CV_CN_SHIFT);

  switch ( depth ) {
    case CV_8U:  r = "8U"; break;
    case CV_8S:  r = "8S"; break;
    case CV_16U: r = "16U"; break;
    case CV_16S: r = "16S"; break;
    case CV_32S: r = "32S"; break;
    case CV_32F: r = "32F"; break;
    case CV_64F: r = "64F"; break;
    default:     r = "User"; break;
  }

  r += "C";
  r += (chans+'0');

  return r;
}

If M is a var of type Mat you can call it like so:

string ty =  type2str( M.type() );
printf("Matrix: %s %dx%d \n", ty.c_str(), M.cols, M.rows );

Will output data such as:

Matrix: 8UC3 640x480 
Matrix: 64FC1 3x2 

Its worth noting that there are also Matrix methods Mat::depth() and Mat::channels(). This function is just a handy way of getting a human readable interpretation from the combination of those two values whose bits are all stored in the same value.

Solution 2 - Opencv

For debugging purposes in case you want to look up a raw Mat::type in a debugger:

C1 C2 C3 C4 C(5) C(6) C(7) C(8)
CV_8U 0 8 16 24 32 40 48 56
CV_8S 1 9 17 25 33 41 49 57
CV_16U 2 10 18 26 34 42 50 58
CV_16S 3 11 19 27 35 43 51 59
CV_32S 4 12 20 28 36 44 52 60
CV_32F 5 13 21 29 37 45 53 61
CV_64F 6 14 22 30 38 46 54 62

So for example, if type = 30 then OpenCV data type is CV_64FC4. If type = 50 then the OpenCV data type is CV_16UC(7).

Solution 3 - Opencv

In OpenCV header "types_c.h" there are a set of defines which generate these, the format is CV_bits{U|S|F}C<number_of_channels>
So for example CV_8UC3 means 8 bit unsigned chars, 3 colour channels - each of these names map onto an arbitrary integer with the macros in that file.

Edit: See "types_c.h" for example:

#define CV_8UC3 CV_MAKETYPE(CV_8U,3)
#define CV_MAKETYPE(depth,cn) (CV_MAT_DEPTH(depth) + (((cn)-1) << CV_CN_SHIFT))

eg.
depth = CV_8U = 0
cn = 3
CV_CN_SHIFT = 3

CV_MAT_DEPTH(0) = 0
(((cn)-1) << CV_CN_SHIFT) = (3-1) << 3 = 2<<3 = 16

So CV_8UC3 = 16 but you aren't supposed to use this number, just check type() == CV_8UC3 if you need to know what type an internal OpenCV array is.
Remember OpenCV will convert the jpeg into BGR (or grey scale if you pass '0' to imread) - so it doesn't tell you anything about the original file.

Solution 4 - Opencv

I've added some usability to the function from the answer by @Octopus, for debugging purposes.

void MatType( Mat inputMat )
{
	int inttype = inputMat.type();

	string r, a;
	uchar depth = inttype & CV_MAT_DEPTH_MASK;
	uchar chans = 1 + (inttype >> CV_CN_SHIFT);
	switch ( depth ) {
		case CV_8U:  r = "8U";   a = "Mat.at<uchar>(y,x)"; break;  
		case CV_8S:  r = "8S";   a = "Mat.at<schar>(y,x)"; break;  
		case CV_16U: r = "16U";  a = "Mat.at<ushort>(y,x)"; break; 
		case CV_16S: r = "16S";  a = "Mat.at<short>(y,x)"; break; 
		case CV_32S: r = "32S";  a = "Mat.at<int>(y,x)"; break; 
		case CV_32F: r = "32F";  a = "Mat.at<float>(y,x)"; break; 
		case CV_64F: r = "64F";  a = "Mat.at<double>(y,x)"; break; 
		default:     r = "User"; a = "Mat.at<UKNOWN>(y,x)"; break; 
	}	
	r += "C";
	r += (chans+'0');
	cout << "Mat is of type " << r << " and should be accessed with " << a << endl;
	
}

Solution 5 - Opencv

This was answered by a few others but I found a solution that worked really well for me.

System.out.println(CvType.typeToString(yourMat.type()));

Solution 6 - Opencv

Base on @Matt Edding's comment (Thanks Mat(T) pun intended ;)):

cout << cv::typeToString(inputMat.type()) << endl;

Works like a charm.

Attributions

All content for this solution is sourced from the original question on Stackoverflow.

The content on this page is licensed under the Attribution-ShareAlike 4.0 International (CC BY-SA 4.0) license.

Content TypeOriginal AuthorOriginal Content on Stackoverflow
QuestionTae-Sung ShinView Question on Stackoverflow
Solution 1 - OpencvOctopusView Answer on Stackoverflow
Solution 2 - OpencvemptyView Answer on Stackoverflow
Solution 3 - OpencvMartin BeckettView Answer on Stackoverflow
Solution 4 - Opencvshahar_mView Answer on Stackoverflow
Solution 5 - OpencvProgrammingCuberView Answer on Stackoverflow
Solution 6 - OpencvYScharfView Answer on Stackoverflow