OpenCV模块介绍
- Core
- Image Processing
- video
- feature2d
- objdetect
- highgui
- Video I/O
- GPU
CV_EXPORTS说明
saturate_cast
@param v Function parameter.
@sa add, subtract, multiply, divide, Mat::convertTo
*/
template<typename _Tp> static inline _Tp saturate_cast(uchar v) { return _Tp(v); }
/** @overload */
template<typename _Tp> static inline _Tp saturate_cast(schar v) { return _Tp(v); }
/** @overload */
template<typename _Tp> static inline _Tp saturate_cast(ushort v) { return _Tp(v); }
/** @overload */
template<typename _Tp> static inline _Tp saturate_cast(short v) { return _Tp(v); }
/** @overload */
template<typename _Tp> static inline _Tp saturate_cast(unsigned v) { return _Tp(v); }
/** @overload */
template<typename _Tp> static inline _Tp saturate_cast(int v) { return _Tp(v); }
/** @overload */
template<typename _Tp> static inline _Tp saturate_cast(float v) { return _Tp(v); }
/** @overload */
template<typename _Tp> static inline _Tp saturate_cast(double v) { return _Tp(v); }
/** @overload */
template<typename _Tp> static inline _Tp saturate_cast(int64 v) { return _Tp(v); }
/** @overload */
template<typename _Tp> static inline _Tp saturate_cast(uint64 v) { return _Tp(v); }
template<> inline uchar saturate_cast<uchar>(schar v) { return (uchar)std::max((int)v, 0); }
template<> inline uchar saturate_cast<uchar>(ushort v) { return (uchar)std::min((unsigned)v, (unsigned)UCHAR_MAX); }
template<> inline uchar saturate_cast<uchar>(int v) { return (uchar)((unsigned)v <= UCHAR_MAX ? v : v > 0 ? UCHAR_MAX : 0); }
template<> inline uchar saturate_cast<uchar>(short v) { return saturate_cast<uchar>((int)v); }
template<> inline uchar saturate_cast<uchar>(unsigned v) { return (uchar)std::min(v, (unsigned)UCHAR_MAX); }
template<> inline uchar saturate_cast<uchar>(float v) { int iv = cvRound(v); return saturate_cast<uchar>(iv); }
template<> inline uchar saturate_cast<uchar>(double v) { int iv = cvRound(v); return saturate_cast<uchar>(iv); }
template<> inline uchar saturate_cast<uchar>(int64 v) { return (uchar)((uint64)v <= (uint64)UCHAR_MAX ? v : v > 0 ? UCHAR_MAX : 0); }
template<> inline uchar saturate_cast<uchar>(uint64 v) { return (uchar)std::min(v, (uint64)UCHAR_MAX); }
上述代码节选自
saturate.hpp
可以清楚的看到saturate_cast使用了模板重载以及模板特化技术
CV_8U/CV_8S/CV_16U/CV_16S/CV_32S/CV_32F/CV_64F及相关说明
#define CV_CN_SHIFT 3
#define CV_DEPTH_MAX (1 << CV_CN_SHIFT)
#define CV_8U 0
#define CV_8S 1
#define CV_16U 2
#define CV_16S 3
#define CV_32S 4
#define CV_32F 5
#define CV_64F 6
#define CV_USRTYPE1 7
#define CV_MAT_DEPTH_MASK (CV_DEPTH_MAX - 1)
#define CV_MAT_DEPTH(flags) ((flags) & CV_MAT_DEPTH_MASK)
#define CV_MAKETYPE(depth,cn) (CV_MAT_DEPTH(depth) + (((cn)-1) << CV_CN_SHIFT))
#define CV_MAKE_TYPE CV_MAKETYPE
这里主要对
CV_MAKETYPE
进行说明
比如CV_8U为0,那么CV_8UCX(x=1,2,3,4),计算公式
CV_8UCX = (CV_8U+(X-1)*8)
上述源码中是使用宏定义进行运算
InputArray/OutputArray探究
首先是InputArray/OutputArray的定义,可以看出InputArray/OutputArray是引用类型而且是const,接下来先看_InputArray,之后看_OutputArray,最后再看_InputOutputArray
typedef const _InputArray& InputArray;
typedef InputArray InputArrayOfArrays;
typedef const _OutputArray& OutputArray;
typedef OutputArray OutputArrayOfArrays;
typedef const _InputOutputArray& InputOutputArray;
typedef InputOutputArray InputOutputArrayOfArrays;
_InputArray
在OpenC开篇介绍中对InputArray的介绍就是一种代理(proxy)类,而且是只读的,从上面代码片段也可以看出,const引用,在OpenCV中有这样一段话
where InputArray is a class that can be constructed from Mat, Mat< T>, Matx< T, m, n>, std::vector< T>, std::vector< std::vector< T> >, std::vector< Mat>, std::vector< Mat_< T> >, UMat, std::vector< UMat> or double. It can also be constructed from a matrix expression.
其实在_InputArray类中定义了相应的枚举值表示对应可以代理的类型,OpenCV文档中是有的,这里就不列举出来了
在介绍_InputArray类的构造函数之前必须介绍_InputArray的两个私有成员函数
void init(int _flags, const void* _obj);
void init(int _flags, const void* _obj, Size _sz);
这两个成员函数的定义在mat.inl.hpp中如下:
inline void _InputArray::init(int _flags, const void* _obj)
{ flags = _flags; obj = (void*)_obj; }
inline void _InputArray::init(int _flags, const void* _obj, Size _sz)
{ flags = _flags; obj = (void*)_obj; sz = _sz; }
这里说明一下
- flags表示的为类型,通过阅读源码发现flags=type+ACCESS_READ(type为_InputArray中的枚举值,ACCESS_READ为mat.hpp中定义的枚举值,ACCESS_READ是针对_InputArray而言的,表示只读)
- obj就是具体需要读取的对象,如Mat,Matx,vector<>
- sz一般用于Matx
- 这三个都是私有成员变量
下面只罗列部分构造函数,这些内联构造函数调用init函数进行初始化,有关函数模板的构造函数,这里没有列举
inline _InputArray::_InputArray() { init(NONE, 0); }
inline _InputArray::_InputArray(int _flags, void* _obj) { init(_flags, _obj); }
inline _InputArray::_InputArray(const Mat& m) { init(MAT+ACCESS_READ, &m); }
inline _InputArray::_InputArray(const std::vector<Mat>& vec) { init(STD_VECTOR_MAT+ACCESS_READ, &vec); }
inline _InputArray::_InputArray(const UMat& m) { init(UMAT+ACCESS_READ, &m); }
inline _InputArray::_InputArray(const std::vector<UMat>& vec) { init(STD_VECTOR_UMAT+ACCESS_READ, &vec); }
_InputArray其他成员函数就不再列举,因为大多数的成员函数转换成原本对应的类型,原理都大同小异,首先判断flags,然后定出类型,将obj转换成对应的类型,进行操作
_OutputArray
_OutputArray共有继承_InputArray,首先介绍其构造函数,节选
inline _OutputArray::_OutputArray() { init(ACCESS_WRITE, 0); }
inline _OutputArray::_OutputArray(int _flags, void* _obj) { init(_flags|ACCESS_WRITE, _obj); }
inline _OutputArray::_OutputArray(Mat& m) { init(MAT+ACCESS_WRITE, &m); }
inline _OutputArray::_OutputArray(std::vector<Mat>& vec) { init(STD_VECTOR_MAT+ACCESS_WRITE, &vec); }
inline _OutputArray::_OutputArray(UMat& m) { init(UMAT+ACCESS_WRITE, &m); }
inline _OutputArray::_OutputArray(std::vector<UMat>& vec) { init(STD_VECTOR_UMAT+ACCESS_WRITE, &vec); }
可以看出其构造函数调用了父类的init函数只是flags=type+ACCESS_WRITE
_OutputArray中getXXX函数返回的是obj的引用,而_InputArray返回的不是引用,
同时_OutputArray新增的一些成员函数,也主要是对obj成员进行操作,即可以更改obj中的数据
总而言之_OutputArray提供了对obj成员进行改变的一系列成员函数
_InputOutputArray
_InputOutputArray公有继承自_OutputArray,它本身没有增加新的成员函数,定义了一系列构造函数,构造函数实现方式和_OutputArray类似,调用init函数,这里需要注意的是flags=type+ACCESS_RW这里ACCESS_RW表示可读写
其他没有太大变化