这是一个中间类,为OPENCV的函数传递只读的参数
其定义可以如下所示:
typedef const _InputArray& InputArray;//将输入参数定义为引用常量,不可修改,不会拷贝传参
_InputArray 是一个可以通过 `Mat`, `Mat_- 如果用户想自己设计函数或者类方法来操作复合类型的数组, 可以针对对应的参数使用 InputArray (或 OutputArray). 函数内 部需要使用.
_InputArray::getMat() 方法来为数组构建矩阵头部(并不拷贝数据). _InputArray::kind() 可以用来区分 Mat 和 `vector<>` 等,但一般情况下不需要.
这是一个函数使用 InputArray的方法 :
std::vector vec;
// points or a circle
for( int i = 0; i < 30; i++ )
vec.push_back(Point2f((float)(100 + 30*cos(i*CV_PI*2/5)),
(float)(100 - 30*sin(i*CV_PI*2/5))));
cv::transform(vec, vec, cv::Matx23f(0.707, -0.707, 10, 0.707, 0.707, 20));
其中,我们使用一个STL向量来存储点,然后在原址中利用内联形式创建的矩阵`Matx void myAffineTransform(InputArray _src, OutputArray _dst, InputArray _m)
{
// get Mat headers for input arrays. This is O(1) operation,
// unless _src and/or _m are matrix expressions.
Mat src = _src.getMat(), m = _m.getMat();
CV_Assert( src.type() == CV_32FC2 && m.type() == CV_32F && m.size() == Size(3, 2) );
// [re]create the output array so that it has the proper size and type.
// In case of Mat it calls Mat::create, in case of STL vector it calls vector::resize.
_dst.create(src.size(), src.type());
Mat dst = _dst.getMat();
for( int i = 0; i < src.rows; i++ )
for( int j = 0; j < src.cols; j++ )
{
Point2f pt = src.at(i, j);
dst.at(i, j) = Point2f(m.at(0, 0)*pt.x +
m.at(0, 1)*pt.y +
m.at(0, 2),
m.at(1, 0)*pt.x +
m.at(1, 1)*pt.y +
m.at(1, 2));
}
}
有另外一个相关的类型, InputArrayOfArrays,目前是InputArray的别名:
typedef InputArray InputArrayOfArrays;
它表示向量的向量或者矩阵的向量. 在生成 Python/Java 等封装时需要一个单独的别名. 但在实现层次上两个是一致的, 但 _InputArray::getMat(idx) 用来获取 idx-th 元素(针对最外一层vector)的头部而 _InputArray::size().area() 用来获取元素的个数(针对最外一层vector).
//////////////////////// Input/Output Array Arguments /////////////////////////////////
class CV_EXPORTS _InputArray // class 和 类名之间添加修饰符,主要表示这个类以后可能用于导入或导出
{
public:
enum {
KIND_SHIFT = 16,
FIXED_TYPE = 0x8000 << KIND_SHIFT,
FIXED_SIZE = 0x4000 << KIND_SHIFT,
KIND_MASK = 31 << KIND_SHIFT,
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,
CUDA_HOST_MEM = 8 << KIND_SHIFT,
CUDA_GPU_MAT = 9 << KIND_SHIFT,
UMAT =10 << KIND_SHIFT,
STD_VECTOR_UMAT =11 << KIND_SHIFT,
STD_BOOL_VECTOR =12 << KIND_SHIFT,
STD_VECTOR_CUDA_GPU_MAT = 13 << KIND_SHIFT,
STD_ARRAY =14 << KIND_SHIFT,
STD_ARRAY_MAT =15 << KIND_SHIFT
};
//构造函数
_InputArray();
_InputArray(int _flags, void* _obj);
_InputArray(const Mat& m);
_InputArray(const MatExpr& expr);
_InputArray(const std::vector& vec);
template _InputArray(const Mat_<_Tp>& m);
template _InputArray(const std::vector<_Tp>& vec);
_InputArray(const std::vector& vec);
template _InputArray(const std::vector >& vec);
_InputArray(const std::vector >&);
template _InputArray(const std::vector >& vec);
template _InputArray(const _Tp* vec, int n);
template _InputArray(const Matx<_Tp, m, n>& matx);
_InputArray(const double& val);
_InputArray(const cuda::GpuMat& d_mat);
_InputArray(const std::vector& d_mat_array);
_InputArray(const ogl::Buffer& buf);
_InputArray(const cuda::HostMem& cuda_mem);
template _InputArray(const cudev::GpuMat_<_Tp>& m);
_InputArray(const UMat& um);
_InputArray(const std::vector& umv);
#ifdef CV_CXX_STD_ARRAY
template _InputArray(const std::array<_Tp, _Nm>& arr);
template _InputArray(const std::array& arr);
#endif
//getXX函数成员
Mat getMat(int idx=-1) const;
Mat getMat_(int idx=-1) const;
UMat getUMat(int idx=-1) const;
void getMatVector(std::vector& mv) const;
void getUMatVector(std::vector& umv) const;
void getGpuMatVector(std::vector& gpumv) const;
cuda::GpuMat getGpuMat() const;
ogl::Buffer getOGlBuffer() const;
int getFlags() const;
void* getObj() const;
Size getSz() const;
int kind() const;
int dims(int i=-1) const;
int cols(int i=-1) const;
int rows(int i=-1) const;
Size size(int i=-1) const;
int sizend(int* sz, int i=-1) const;
bool sameSize(const _InputArray& arr) const;
size_t total(int i=-1) const;
int type(int i=-1) const;
int depth(int i=-1) const;
int channels(int i=-1) const;
bool isContinuous(int i=-1) const;
bool isSubmatrix(int i=-1) const;
bool empty() const;
void copyTo(const _OutputArray& arr) const;
void copyTo(const _OutputArray& arr, const _InputArray & mask) const;
size_t offset(int i=-1) const;
size_t step(int i=-1) const;
bool isMat() const;
bool isUMat() const;
bool isMatVector() const;
bool isUMatVector() const;
bool isMatx() const;
bool isVector() const;
bool isGpuMatVector() const;
~_InputArray();
protected:
int flags;
void* obj;
Size sz;
void init(int _flags, const void* _obj);
void init(int _flags, const void* _obj, Size _sz);
};
这个类型与 InputArray类似,但是这个是用于 输入/输出 和输出 函数的参数。就像InputArray一样, OpenCV 用户并不需要关注OutputArray, 只需要传递 `Mat`,`vector
关于可选的参数: 如果用户并不需要确切的输出数组来进行计算并返回,可以传递传递cv::noArray,就像输入数组中的可选参数一样。在实现的层面上,使用使用_OutputArray::needed() 来核实是否需要计算输出数组。
typedef OutputArray OutputArrayOfArrays;
typedef OutputArray InputOutputArray;
typedef OutputArray InputOutputArrayOfArrays;
class CV_EXPORTS _OutputArray : public _InputArray//继承于输入数组
{
public:
enum
{
DEPTH_MASK_8U = 1 << CV_8U,
DEPTH_MASK_8S = 1 << CV_8S,
DEPTH_MASK_16U = 1 << CV_16U,
DEPTH_MASK_16S = 1 << CV_16S,
DEPTH_MASK_32S = 1 << CV_32S,
DEPTH_MASK_32F = 1 << CV_32F,
DEPTH_MASK_64F = 1 << CV_64F,
DEPTH_MASK_ALL = (DEPTH_MASK_64F<<1)-1,
DEPTH_MASK_ALL_BUT_8S = DEPTH_MASK_ALL & ~DEPTH_MASK_8S,
DEPTH_MASK_FLT = DEPTH_MASK_32F + DEPTH_MASK_64F
};
//构造函数
_OutputArray();
_OutputArray(int _flags, void* _obj);
_OutputArray(Mat& m);
_OutputArray(std::vector& vec);
_OutputArray(cuda::GpuMat& d_mat);
_OutputArray(std::vector& d_mat);
_OutputArray(ogl::Buffer& buf);
_OutputArray(cuda::HostMem& cuda_mem);
template _OutputArray(cudev::GpuMat_<_Tp>& m);
template _OutputArray(std::vector<_Tp>& vec);
_OutputArray(std::vector& vec);
template _OutputArray(std::vector >& vec);
_OutputArray(std::vector >&);
template _OutputArray(std::vector >& vec);
template _OutputArray(Mat_<_Tp>& m);
template _OutputArray(_Tp* vec, int n);
template _OutputArray(Matx<_Tp, m, n>& matx);
_OutputArray(UMat& m);
_OutputArray(std::vector& vec);
_OutputArray(const Mat& m);
_OutputArray(const std::vector& vec);
_OutputArray(const cuda::GpuMat& d_mat);
_OutputArray(const std::vector& d_mat);
_OutputArray(const ogl::Buffer& buf);
_OutputArray(const cuda::HostMem& cuda_mem);
template _OutputArray(const cudev::GpuMat_<_Tp>& m);
template _OutputArray(const std::vector<_Tp>& vec);
template _OutputArray(const std::vector >& vec);
template _OutputArray(const std::vector >& vec);
template _OutputArray(const Mat_<_Tp>& m);
template _OutputArray(const _Tp* vec, int n);
template _OutputArray(const Matx<_Tp, m, n>& matx);
_OutputArray(const UMat& m);
_OutputArray(const std::vector& vec);
#ifdef CV_CXX_STD_ARRAY
template _OutputArray(std::array<_Tp, _Nm>& arr);
template _OutputArray(const std::array<_Tp, _Nm>& arr);
template _OutputArray(std::array& arr);
template _OutputArray(const std::array& arr);
#endif
bool fixedSize() const;
bool fixedType() const;
bool needed() const;
Mat& getMatRef(int i=-1) const;
UMat& getUMatRef(int i=-1) const;
cuda::GpuMat& getGpuMatRef() const;
std::vector& getGpuMatVecRef() const;
ogl::Buffer& getOGlBufferRef() const;
cuda::HostMem& getHostMemRef() const;
void create(Size sz, int type, int i=-1, bool allowTransposed=false, int fixedDepthMask=0) const;
void create(int rows, int cols, int type, int i=-1, bool allowTransposed=false, int fixedDepthMask=0) const;
void create(int dims, const int* size, int type, int i=-1, bool allowTransposed=false, int fixedDepthMask=0) const;
void createSameSize(const _InputArray& arr, int mtype) const;
void release() const;
void clear() const;
void setTo(const _InputArray& value, const _InputArray & mask = _InputArray()) const;
void assign(const UMat& u) const;
void assign(const Mat& m) const;
void assign(const std::vector& v) const;
void assign(const std::vector& v) const;
};
class CV_EXPORTS _InputOutputArray : public _OutputArray
{
public:
_InputOutputArray();
_InputOutputArray(int _flags, void* _obj);
_InputOutputArray(Mat& m);
_InputOutputArray(std::vector& vec);
_InputOutputArray(cuda::GpuMat& d_mat);
_InputOutputArray(ogl::Buffer& buf);
_InputOutputArray(cuda::HostMem& cuda_mem);
template _InputOutputArray(cudev::GpuMat_<_Tp>& m);
template _InputOutputArray(std::vector<_Tp>& vec);
_InputOutputArray(std::vector& vec);
template _InputOutputArray(std::vector >& vec);
template _InputOutputArray(std::vector >& vec);
template _InputOutputArray(Mat_<_Tp>& m);
template _InputOutputArray(_Tp* vec, int n);
template _InputOutputArray(Matx<_Tp, m, n>& matx);
_InputOutputArray(UMat& m);
_InputOutputArray(std::vector& vec);
_InputOutputArray(const Mat& m);
_InputOutputArray(const std::vector& vec);
_InputOutputArray(const cuda::GpuMat& d_mat);
_InputOutputArray(const std::vector& d_mat);
_InputOutputArray(const ogl::Buffer& buf);
_InputOutputArray(const cuda::HostMem& cuda_mem);
template _InputOutputArray(const cudev::GpuMat_<_Tp>& m);
template _InputOutputArray(const std::vector<_Tp>& vec);
template _InputOutputArray(const std::vector >& vec);
template _InputOutputArray(const std::vector >& vec);
template _InputOutputArray(const Mat_<_Tp>& m);
template _InputOutputArray(const _Tp* vec, int n);
template _InputOutputArray(const Matx<_Tp, m, n>& matx);
_InputOutputArray(const UMat& m);
_InputOutputArray(const std::vector& vec);
#ifdef CV_CXX_STD_ARRAY
template _InputOutputArray(std::array<_Tp, _Nm>& arr);
template _InputOutputArray(const std::array<_Tp, _Nm>& arr);
template _InputOutputArray(std::array& arr);
template _InputOutputArray(const std::array& arr);
#endif
};
CV__DEBUG_NS_END
//别名声明
typedef const _InputArray& InputArray;
typedef InputArray InputArrayOfArrays;
typedef const _OutputArray& OutputArray;
typedef OutputArray OutputArrayOfArrays;
typedef const _InputOutputArray& InputOutputArray;
typedef InputOutputArray InputOutputArrayOfArrays;
CV_EXPORTS InputOutputArray noArray();