OpenCV的Mat型別以及基本函式使用
Mat和IplImage的區別
Mat和IplImage的主要區別
在OpenCV中IplImage是表示一個影像的結構體,也是從OpenCV1.0到目前最為重要的一個結構;在之前的影像表示用IplImage,而且之前的OpenCV是用C語言撰寫的,提供的介面也是C語言介面,
Mat是后來OpenCV封裝的一個C++類,用來表示一個影像,和IplImage表示基本一致,但是Mat還添加了一些影像函式,
IplImage
IplImage資料結構的定義在opencv\build\include\opencv2\core\types_c.h檔案中,
typedef struct _IplImage
{
int nSize; /* sizeof(IplImage) */
int ID; /* version (=0)*/
int nChannels; /* Most of OpenCV functions support 1,2,3 or 4 channels */
int alphaChannel; /* Ignored by OpenCV */
int depth; /* Pixel depth in bits: IPL_DEPTH_8U, IPL_DEPTH_8S, IPL_DEPTH_16S,
IPL_DEPTH_32S, IPL_DEPTH_32F and IPL_DEPTH_64F are supported. */
char colorModel[4]; /* Ignored by OpenCV */
char channelSeq[4]; /* ditto */
int dataOrder; /* 0 - interleaved color channels, 1 - separate color channels.
cvCreateImage can only create interleaved images */
int origin; /* 0 - top-left origin,
1 - bottom-left origin (Windows bitmaps style). */
int align; /* Alignment of image rows (4 or 8).
OpenCV ignores it and uses widthStep instead. */
int width; /* Image width in pixels. */
int height; /* Image height in pixels. */
struct _IplROI *roi; /* Image ROI. If NULL, the whole image is selected. */
struct _IplImage *maskROI; /* Must be NULL. */
void *imageId; /* " " */
struct _IplTileInfo *tileInfo; /* " " */
int imageSize; /* Image data size in bytes
(==image->height*image->widthStep
in case of interleaved data)*/
char *imageData; /* Pointer to aligned image data. */
int widthStep; /* Size of aligned image row in bytes. */
int BorderMode[4]; /* Ignored by OpenCV. */
int BorderConst[4]; /* Ditto. */
char *imageDataOrigin; /* Pointer to very origin of image data
(not necessarily aligned) -
needed for correct deallocation */
}
IplImage;
可見,IplImage是一個表示影像的結構體:C語言操作OpenCV的資料結構,地位等同于Mat,可以說是歷史版本了,
Mat
Mat這個資料結構定義在opencv\build\include\opencv2\core\core.hpp這個檔案,
class CV_EXPORTS Mat
{
public:
//! default constructor
Mat();
//! constructs 2D matrix of the specified size and type
// (_type is CV_8UC1, CV_64FC3, CV_32SC(12) etc.)
Mat(int rows, int cols, int type);
Mat(Size size, int type);
//! constucts 2D matrix and fills it with the specified value _s.
Mat(int rows, int cols, int type, const Scalar& s);
Mat(Size size, int type, const Scalar& s);
//! constructs n-dimensional matrix
Mat(int ndims, const int* sizes, int type);
Mat(int ndims, const int* sizes, int type, const Scalar& s);
//! copy constructor
Mat(const Mat& m);
//! constructor for matrix headers pointing to user-allocated data
Mat(int rows, int cols, int type, void* data, size_t step=AUTO_STEP);
Mat(Size size, int type, void* data, size_t step=AUTO_STEP);
Mat(int ndims, const int* sizes, int type, void* data, const size_t* steps=0);
//! creates a matrix header for a part of the bigger matrix
Mat(const Mat& m, const Range& rowRange, const Range& colRange=Range::all());
Mat(const Mat& m, const Rect& roi);
Mat(const Mat& m, const Range* ranges);
//! converts old-style CvMat to the new matrix; the data is not copied by default
Mat(const CvMat* m, bool copyData=https://www.cnblogs.com/CHLL55/p/false);
//! converts old-style CvMatND to the new matrix; the data is not copied by default
Mat(const CvMatND* m, bool copyData=false);
//! converts old-style IplImage to the new matrix; the data is not copied by default
Mat(const IplImage* img, bool copyData=false);
//! builds matrix from std::vector with or without copying the data
......
protected:
void initEmpty();
};
Mat是OpenCV最基本的資料結構,Mat即矩陣(Matrix)的縮寫我們在讀取圖片的時候就是將圖片定義為Mat型別,其多載的建構式一大堆,
其中有一個建構式可以很方便的直接將IplImage轉化為Mat
Mat(const IplImage* img, bool copyData=https://www.cnblogs.com/CHLL55/p/false);
基本函式使用
imread
功能:從一個檔案中載入圖片
定義:
Mat imread( const string& filename, int flags=1 );
■第一個引數,const string&型別的filename,這是我們需要載入的圖片路徑名,
在Windows作業系統下,OpenCV的imread函式支持常用的圖片型別,比如bmp,jpg,jpeg,png等等,
■第二個引數,int型別的flags,為載入標識,它指定一個加載影像的顏色型別,可以看到它自帶預設值1.所以有時候這個引數在呼叫時我們可以忽略,如果在呼叫時忽略這個引數,就表示載入三通道的彩色影像,具體原因看下面的解釋,
flags是int型的變數,我們可以按如下方式取值:
- flags >0回傳一個3通道的彩色影像,
- flags =0回傳灰度影像,
- flags <0回傳包含Alpha通道的加載的影像,
需要注意的點:輸出的影像默認情況下是不載入Alpha通道進來的,如果我們需要載入Alpha通道的話呢,這里就需要取負值,
所以默認值flags=1表示載入三通道的彩色影像,
imshow
功能:顯示一個影像
定義:
void imshow(const string& winname, InputArray mat);
■ 第一個引數,const string&型別的winname,填需要顯示的視窗標識名稱,
■ 第二個引數,InputArray 型別的mat,填需要顯示的影像,
InputArray 型別是什么型別?
通過轉到定義,我們可以在opencv\build\include\opencv2\highgui\highgui.hpp檔案中找到imshow的原型:
CV_EXPORTS_W void imshow(const string& winname, InputArray mat);
進一步對InputArray轉到定義,在opencv\build\include\opencv2\core\core.hpp檔案中查到一個typedef宣告:
typedef const _InputArray& InputArray;
這其實一個型別宣告參考,就是說_InputArray和InputArray是一個意思,然后再次對_InputArray進行轉到定義,終于,在opencv\build\include\opencv2\core\core.hpp檔案中發現了InputArray的真身:
class CV_EXPORTS _InputArray
{
public:
enum {
KIND_SHIFT = 16,
FIXED_TYPE = 0x8000 << KIND_SHIFT,
FIXED_SIZE = 0x4000 << KIND_SHIFT,
KIND_MASK = ~(FIXED_TYPE|FIXED_SIZE) - (1 << KIND_SHIFT) + 1,
NONE = 0 << KIND_SHIFT,
MAT = 1 << KIND_SHIFT,
MATX = 2 << KIND_SHIFT,
STD_VECTOR = 3 << KIND_SHIFT,
STD_VECTOR_VECTOR = 4 << KIND_SHIFT,
STD_VECTOR_MAT = 5 << KIND_SHIFT,
EXPR = 6 << KIND_SHIFT,
OPENGL_BUFFER = 7 << KIND_SHIFT,
OPENGL_TEXTURE = 8 << KIND_SHIFT,
GPU_MAT = 9 << KIND_SHIFT,
OCL_MAT =10 << KIND_SHIFT
};
_InputArray();
_InputArray(const Mat& m);
_InputArray(const MatExpr& expr);
template<typename _Tp> _InputArray(const _Tp* vec, int n);
template<typename _Tp> _InputArray(const vector<_Tp>& vec);
template<typename _Tp> _InputArray(const vector<vector<_Tp> >& vec);
_InputArray(const vector<Mat>& vec);
template<typename _Tp> _InputArray(const vector<Mat_<_Tp> >& vec);
template<typename _Tp> _InputArray(const Mat_<_Tp>& m);
template<typename _Tp, int m, int n> _InputArray(const Matx<_Tp, m, n>& matx);
_InputArray(const Scalar& s);
_InputArray(const double& val);
// < Deprecated
_InputArray(const GlBuffer& buf);
_InputArray(const GlTexture& tex);
// >
_InputArray(const gpu::GpuMat& d_mat);
_InputArray(const ogl::Buffer& buf);
_InputArray(const ogl::Texture2D& tex);
virtual Mat getMat(int i=-1) const;
virtual void getMatVector(vector<Mat>& mv) const;
// < Deprecated
virtual GlBuffer getGlBuffer() const;
virtual GlTexture getGlTexture() const;
// >
virtual gpu::GpuMat getGpuMat() const;
/*virtual*/ ogl::Buffer getOGlBuffer() const;
/*virtual*/ ogl::Texture2D getOGlTexture2D() const;
virtual int kind() const;
virtual Size size(int i=-1) const;
virtual size_t total(int i=-1) const;
virtual int type(int i=-1) const;
virtual int depth(int i=-1) const;
virtual int channels(int i=-1) const;
virtual bool empty() const;
#ifdef OPENCV_CAN_BREAK_BINARY_COMPATIBILITY
virtual ~_InputArray();
#endif
int flags;
void* obj;
Size sz;
};
可以看到,_InputArray類的里面首先定義了一個列舉,然后定了各個建構式和虛函式,很多時候,遇到函式原型中的InputArray型別,我們把它簡單地當做Mat型別就行了,
imshow 函式用于在指定的視窗中顯示影像,如果視窗是用CV_WINDOW_AUTOSIZE(默認值)標志創建的,那么顯示影像原始大小,否則,將影像進行縮放以適合視窗,而imshow 函式縮放影像,取決于影像的深度:
- 如果載入的影像是8位無符號型別(8-bit unsigned),就顯示影像本來的樣子,
- 如果影像是16位無符號型別(16-bit unsigned)或32位整型(32-bit integer),便用像素值除以256,也就是說,值的范圍是[0,255 x 256]映射到[0,255],
- 如果影像是32位浮點型(32-bit floating-point),像素值便要乘以255,也就是說,該值的范圍是[0,1]映射到[0,255],
imwrite
功能:輸出影像到檔案
定義:
bool imwrite( const string& filename, InputArray img,
const vector<int>& params=vector<int>());
■ 第一個引數,const string&型別的filename,填需要寫入的檔案名就行了,帶上后綴,比如,“123.jpg”這樣,
■ 第二個引數,InputArray型別的img,一般填一個Mat型別的影像資料就行了,
■ 第三個引數,const vector<int>&型別的params,表示為特定格式保存的引數編碼,它有默認值vector<int>(),所以一般情況下不需要填寫,
cvtcolor
功能:將一個影像的顏色空間轉換到另一種(Converts an image from one color space to another.)
參考:cvtcolor
定義:
void cvtColor( InputArray src, OutputArray dst, int code, int dstCn=0 );
■ 第一個引數,InputArray型別的src ,-- Source image
■ 第二個引數,OutputArray型別的dst,Destination image of the same size and depth as src
■ 第三個引數,int型別的code,顏色空間變換代碼Color space conversion code,
具體的變換代碼參見:opencv\build\include\opencv2\imgproc\types_c.h檔案中的第87行,列舉型別,
/* Constants for color conversion */
enum
{
CV_BGR2BGRA =0,
CV_RGB2RGBA =CV_BGR2BGRA,
CV_BGRA2BGR =1,
CV_RGBA2RGB =CV_BGRA2BGR,
CV_BGR2RGBA =2,
CV_RGB2BGRA =CV_BGR2RGBA,
CV_RGBA2BGR =3,
CV_BGRA2RGB =CV_RGBA2BGR,
CV_BGR2RGB =4,
CV_RGB2BGR =CV_BGR2RGB,
CV_BGRA2RGBA =5,
CV_RGBA2BGRA =CV_BGRA2RGBA,
CV_BGR2GRAY =6,
CV_RGB2GRAY =7,
CV_GRAY2BGR =8,
CV_GRAY2RGB =CV_GRAY2BGR,
CV_GRAY2BGRA =9,
CV_GRAY2RGBA =CV_GRAY2BGRA,
CV_BGRA2GRAY =10,
CV_RGBA2GRAY =11,
CV_BGR2BGR565 =12,
CV_RGB2BGR565 =13,
CV_BGR5652BGR =14,
CV_BGR5652RGB =15,
CV_BGRA2BGR565 =16,
CV_RGBA2BGR565 =17,
CV_BGR5652BGRA =18,
CV_BGR5652RGBA =19,
CV_GRAY2BGR565 =20,
CV_BGR5652GRAY =21,
CV_BGR2BGR555 =22,
CV_RGB2BGR555 =23,
CV_BGR5552BGR =24,
CV_BGR5552RGB =25,
CV_BGRA2BGR555 =26,
CV_RGBA2BGR555 =27,
CV_BGR5552BGRA =28,
CV_BGR5552RGBA =29,
CV_GRAY2BGR555 =30,
CV_BGR5552GRAY =31,
CV_BGR2XYZ =32,
CV_RGB2XYZ =33,
CV_XYZ2BGR =34,
CV_XYZ2RGB =35,
CV_BGR2YCrCb =36,
CV_RGB2YCrCb =37,
CV_YCrCb2BGR =38,
CV_YCrCb2RGB =39,
CV_BGR2HSV =40,
CV_RGB2HSV =41,
CV_BGR2Lab =44,
CV_RGB2Lab =45,
CV_BayerBG2BGR =46,
CV_BayerGB2BGR =47,
CV_BayerRG2BGR =48,
CV_BayerGR2BGR =49,
CV_BayerBG2RGB =CV_BayerRG2BGR,
CV_BayerGB2RGB =CV_BayerGR2BGR,
CV_BayerRG2RGB =CV_BayerBG2BGR,
CV_BayerGR2RGB =CV_BayerGB2BGR,
CV_BGR2Luv =50,
CV_RGB2Luv =51,
CV_BGR2HLS =52,
CV_RGB2HLS =53,
CV_HSV2BGR =54,
CV_HSV2RGB =55,
CV_Lab2BGR =56,
CV_Lab2RGB =57,
CV_Luv2BGR =58,
CV_Luv2RGB =59,
CV_HLS2BGR =60,
CV_HLS2RGB =61,
CV_BayerBG2BGR_VNG =62,
CV_BayerGB2BGR_VNG =63,
CV_BayerRG2BGR_VNG =64,
CV_BayerGR2BGR_VNG =65,
CV_BayerBG2RGB_VNG =CV_BayerRG2BGR_VNG,
CV_BayerGB2RGB_VNG =CV_BayerGR2BGR_VNG,
CV_BayerRG2RGB_VNG =CV_BayerBG2BGR_VNG,
CV_BayerGR2RGB_VNG =CV_BayerGB2BGR_VNG,
CV_BGR2HSV_FULL = 66,
CV_RGB2HSV_FULL = 67,
CV_BGR2HLS_FULL = 68,
CV_RGB2HLS_FULL = 69,
CV_HSV2BGR_FULL = 70,
CV_HSV2RGB_FULL = 71,
CV_HLS2BGR_FULL = 72,
CV_HLS2RGB_FULL = 73,
CV_LBGR2Lab = 74,
CV_LRGB2Lab = 75,
CV_LBGR2Luv = 76,
CV_LRGB2Luv = 77,
CV_Lab2LBGR = 78,
CV_Lab2LRGB = 79,
CV_Luv2LBGR = 80,
CV_Luv2LRGB = 81,
CV_BGR2YUV = 82,
CV_RGB2YUV = 83,
CV_YUV2BGR = 84,
CV_YUV2RGB = 85,
CV_BayerBG2GRAY = 86,
CV_BayerGB2GRAY = 87,
CV_BayerRG2GRAY = 88,
CV_BayerGR2GRAY = 89,
//YUV 4:2:0 formats family
CV_YUV2RGB_NV12 = 90,
CV_YUV2BGR_NV12 = 91,
CV_YUV2RGB_NV21 = 92,
CV_YUV2BGR_NV21 = 93,
CV_YUV420sp2RGB = CV_YUV2RGB_NV21,
CV_YUV420sp2BGR = CV_YUV2BGR_NV21,
CV_YUV2RGBA_NV12 = 94,
CV_YUV2BGRA_NV12 = 95,
CV_YUV2RGBA_NV21 = 96,
CV_YUV2BGRA_NV21 = 97,
CV_YUV420sp2RGBA = CV_YUV2RGBA_NV21,
CV_YUV420sp2BGRA = CV_YUV2BGRA_NV21,
CV_YUV2RGB_YV12 = 98,
CV_YUV2BGR_YV12 = 99,
CV_YUV2RGB_IYUV = 100,
CV_YUV2BGR_IYUV = 101,
CV_YUV2RGB_I420 = CV_YUV2RGB_IYUV,
CV_YUV2BGR_I420 = CV_YUV2BGR_IYUV,
CV_YUV420p2RGB = CV_YUV2RGB_YV12,
CV_YUV420p2BGR = CV_YUV2BGR_YV12,
CV_YUV2RGBA_YV12 = 102,
CV_YUV2BGRA_YV12 = 103,
CV_YUV2RGBA_IYUV = 104,
CV_YUV2BGRA_IYUV = 105,
CV_YUV2RGBA_I420 = CV_YUV2RGBA_IYUV,
CV_YUV2BGRA_I420 = CV_YUV2BGRA_IYUV,
CV_YUV420p2RGBA = CV_YUV2RGBA_YV12,
CV_YUV420p2BGRA = CV_YUV2BGRA_YV12,
CV_YUV2GRAY_420 = 106,
CV_YUV2GRAY_NV21 = CV_YUV2GRAY_420,
CV_YUV2GRAY_NV12 = CV_YUV2GRAY_420,
CV_YUV2GRAY_YV12 = CV_YUV2GRAY_420,
CV_YUV2GRAY_IYUV = CV_YUV2GRAY_420,
CV_YUV2GRAY_I420 = CV_YUV2GRAY_420,
CV_YUV420sp2GRAY = CV_YUV2GRAY_420,
CV_YUV420p2GRAY = CV_YUV2GRAY_420,
//YUV 4:2:2 formats family
CV_YUV2RGB_UYVY = 107,
CV_YUV2BGR_UYVY = 108,
//CV_YUV2RGB_VYUY = 109,
//CV_YUV2BGR_VYUY = 110,
CV_YUV2RGB_Y422 = CV_YUV2RGB_UYVY,
CV_YUV2BGR_Y422 = CV_YUV2BGR_UYVY,
CV_YUV2RGB_UYNV = CV_YUV2RGB_UYVY,
CV_YUV2BGR_UYNV = CV_YUV2BGR_UYVY,
CV_YUV2RGBA_UYVY = 111,
CV_YUV2BGRA_UYVY = 112,
//CV_YUV2RGBA_VYUY = 113,
//CV_YUV2BGRA_VYUY = 114,
CV_YUV2RGBA_Y422 = CV_YUV2RGBA_UYVY,
CV_YUV2BGRA_Y422 = CV_YUV2BGRA_UYVY,
CV_YUV2RGBA_UYNV = CV_YUV2RGBA_UYVY,
CV_YUV2BGRA_UYNV = CV_YUV2BGRA_UYVY,
CV_YUV2RGB_YUY2 = 115,
CV_YUV2BGR_YUY2 = 116,
CV_YUV2RGB_YVYU = 117,
CV_YUV2BGR_YVYU = 118,
CV_YUV2RGB_YUYV = CV_YUV2RGB_YUY2,
CV_YUV2BGR_YUYV = CV_YUV2BGR_YUY2,
CV_YUV2RGB_YUNV = CV_YUV2RGB_YUY2,
CV_YUV2BGR_YUNV = CV_YUV2BGR_YUY2,
CV_YUV2RGBA_YUY2 = 119,
CV_YUV2BGRA_YUY2 = 120,
CV_YUV2RGBA_YVYU = 121,
CV_YUV2BGRA_YVYU = 122,
CV_YUV2RGBA_YUYV = CV_YUV2RGBA_YUY2,
CV_YUV2BGRA_YUYV = CV_YUV2BGRA_YUY2,
CV_YUV2RGBA_YUNV = CV_YUV2RGBA_YUY2,
CV_YUV2BGRA_YUNV = CV_YUV2BGRA_YUY2,
CV_YUV2GRAY_UYVY = 123,
CV_YUV2GRAY_YUY2 = 124,
//CV_YUV2GRAY_VYUY = CV_YUV2GRAY_UYVY,
CV_YUV2GRAY_Y422 = CV_YUV2GRAY_UYVY,
CV_YUV2GRAY_UYNV = CV_YUV2GRAY_UYVY,
CV_YUV2GRAY_YVYU = CV_YUV2GRAY_YUY2,
CV_YUV2GRAY_YUYV = CV_YUV2GRAY_YUY2,
CV_YUV2GRAY_YUNV = CV_YUV2GRAY_YUY2,
// alpha premultiplication
CV_RGBA2mRGBA = 125,
CV_mRGBA2RGBA = 126,
CV_RGB2YUV_I420 = 127,
CV_BGR2YUV_I420 = 128,
CV_RGB2YUV_IYUV = CV_RGB2YUV_I420,
CV_BGR2YUV_IYUV = CV_BGR2YUV_I420,
CV_RGBA2YUV_I420 = 129,
CV_BGRA2YUV_I420 = 130,
CV_RGBA2YUV_IYUV = CV_RGBA2YUV_I420,
CV_BGRA2YUV_IYUV = CV_BGRA2YUV_I420,
CV_RGB2YUV_YV12 = 131,
CV_BGR2YUV_YV12 = 132,
CV_RGBA2YUV_YV12 = 133,
CV_BGRA2YUV_YV12 = 134,
CV_COLORCVT_MAX = 135
};
■ 第四個引數,int型別的dstCn,dst中的通道數(channel number ),dstCn默認為0,表示 dst中通道數自動從src和code中獲取,
示例:
//將彩色影像image1變換為灰度影像gray_image1
cvtColor(image1,gray_image1,CV_RGB2GRAY);
綜合示例
// VS2010 + OpenCV2.4.9
#include<opencv2/core/core.hpp>
#include<opencv2/highgui/highgui.hpp>
using namespace cv;
int main( )
{
Mat girl=imread("girl.jpg"); //載入影像到Mat
namedWindow("girl.jpg");
imshow("girl.jpg",girl);
//載入圖片
Mat image= imread("11.jpg",199);
//載入后先顯示
namedWindow("11.jpg");
imshow("11.jpg",image);
//輸出一張jpg圖片到工程目錄下
imwrite("10.jpg",image);
waitKey();
return 0;
}
記得幫我點贊哦!
精心整理了計算機各個方向的從入門、進階、實戰的視頻課程和電子書,按照目錄合理分類,總能找到你需要的學習資料,還在等什么?快去關注下載吧!!!

念念不忘,必有回響,小伙伴們幫我點個贊吧,非常感謝,
我是職場亮哥,YY高級軟體工程師、四年作業經驗,拒絕咸魚爭當龍頭的斜杠程式員,
聽我說,進步多,程式人生一把梭
如果有幸能幫到你,請幫我點個【贊】,給個關注,如果能順帶評論給個鼓勵,將不勝感激,
職場亮哥文章串列:更多文章

本人所有文章、回答都與著作權保護平臺有合作,著作權歸職場亮哥所有,未經授權,轉載必究!
轉載請註明出處,本文鏈接:https://www.uj5u.com/qita/104984.html
標籤:其他
上一篇:棋牌游戲匹配
下一篇:大家好像都不認識這個東西。。。
