Skip to content

Commit 636ab09

Browse files
arnaudbrejeonalalek
authored andcommitted
Merge pull request opencv#8535 from arnaudbrejeon:std_array
Add support for std::array<T, N> (opencv#8535) * Add support for std::array<T, N> * Add std::array<Mat, N> support * Remove UMat constructor with std::array parameter
1 parent 2922738 commit 636ab09

File tree

8 files changed

+466
-20
lines changed

8 files changed

+466
-20
lines changed

modules/core/include/opencv2/core/cvdef.h

Lines changed: 15 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -364,6 +364,21 @@ Cv64suf;
364364
# endif
365365
#endif
366366

367+
/****************************************************************************************\
368+
* C++11 std::array *
369+
\****************************************************************************************/
370+
371+
#ifndef CV_CXX_STD_ARRAY
372+
# if __cplusplus >= 201103L
373+
# define CV_CXX_STD_ARRAY 1
374+
# include <array>
375+
# endif
376+
#else
377+
# if CV_CXX_STD_ARRAY == 0
378+
# undef CV_CXX_STD_ARRAY
379+
# endif
380+
#endif
381+
367382
//! @}
368383

369384
#endif // OPENCV_CORE_CVDEF_H

modules/core/include/opencv2/core/mat.hpp

Lines changed: 44 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -165,7 +165,9 @@ class CV_EXPORTS _InputArray
165165
UMAT =10 << KIND_SHIFT,
166166
STD_VECTOR_UMAT =11 << KIND_SHIFT,
167167
STD_BOOL_VECTOR =12 << KIND_SHIFT,
168-
STD_VECTOR_CUDA_GPU_MAT = 13 << KIND_SHIFT
168+
STD_VECTOR_CUDA_GPU_MAT = 13 << KIND_SHIFT,
169+
STD_ARRAY =14 << KIND_SHIFT,
170+
STD_ARRAY_MAT =15 << KIND_SHIFT
169171
};
170172

171173
_InputArray();
@@ -189,6 +191,11 @@ class CV_EXPORTS _InputArray
189191
_InputArray(const UMat& um);
190192
_InputArray(const std::vector<UMat>& umv);
191193

194+
#ifdef CV_CXX_STD_ARRAY
195+
template<typename _Tp, std::size_t _N> _InputArray(const std::array<_Tp, _N>& arr);
196+
template<std::size_t _N> _InputArray(const std::array<Mat, _N>& arr);
197+
#endif
198+
192199
Mat getMat(int idx=-1) const;
193200
Mat getMat_(int idx=-1) const;
194201
UMat getUMat(int idx=-1) const;
@@ -316,6 +323,13 @@ class CV_EXPORTS _OutputArray : public _InputArray
316323
_OutputArray(const UMat& m);
317324
_OutputArray(const std::vector<UMat>& vec);
318325

326+
#ifdef CV_CXX_STD_ARRAY
327+
template<typename _Tp, std::size_t _N> _OutputArray(std::array<_Tp, _N>& arr);
328+
template<typename _Tp, std::size_t _N> _OutputArray(const std::array<_Tp, _N>& arr);
329+
template<std::size_t _N> _OutputArray(std::array<Mat, _N>& arr);
330+
template<std::size_t _N> _OutputArray(const std::array<Mat, _N>& arr);
331+
#endif
332+
319333
bool fixedSize() const;
320334
bool fixedType() const;
321335
bool needed() const;
@@ -374,6 +388,14 @@ class CV_EXPORTS _InputOutputArray : public _OutputArray
374388
template<typename _Tp, int m, int n> _InputOutputArray(const Matx<_Tp, m, n>& matx);
375389
_InputOutputArray(const UMat& m);
376390
_InputOutputArray(const std::vector<UMat>& vec);
391+
392+
#ifdef CV_CXX_STD_ARRAY
393+
template<typename _Tp, std::size_t _N> _InputOutputArray(std::array<_Tp, _N>& arr);
394+
template<typename _Tp, std::size_t _N> _InputOutputArray(const std::array<_Tp, _N>& arr);
395+
template<std::size_t _N> _InputOutputArray(std::array<Mat, _N>& arr);
396+
template<std::size_t _N> _InputOutputArray(const std::array<Mat, _N>& arr);
397+
#endif
398+
377399
};
378400

379401
typedef const _InputArray& InputArray;
@@ -955,6 +977,12 @@ class CV_EXPORTS Mat
955977
*/
956978
template<typename _Tp> explicit Mat(const std::vector<_Tp>& vec, bool copyData=false);
957979

980+
#ifdef CV_CXX_STD_ARRAY
981+
/** @overload
982+
*/
983+
template<typename _Tp, size_t _N> explicit Mat(const std::array<_Tp, _N>& arr, bool copyData=false);
984+
#endif
985+
958986
/** @overload
959987
*/
960988
template<typename _Tp, int n> explicit Mat(const Vec<_Tp, n>& vec, bool copyData=true);
@@ -1575,6 +1603,10 @@ class CV_EXPORTS Mat
15751603
template<typename _Tp, int n> operator Vec<_Tp, n>() const;
15761604
template<typename _Tp, int m, int n> operator Matx<_Tp, m, n>() const;
15771605

1606+
#ifdef CV_CXX_STD_ARRAY
1607+
template<typename _Tp, std::size_t _N> operator std::array<_Tp, _N>() const;
1608+
#endif
1609+
15781610
/** @brief Reports whether the matrix is continuous or not.
15791611
15801612
The method returns true if the matrix elements are stored continuously without gaps at the end of
@@ -2114,6 +2146,10 @@ template<typename _Tp> class Mat_ : public Mat
21142146
explicit Mat_(const Point3_<typename DataType<_Tp>::channel_type>& pt, bool copyData=true);
21152147
explicit Mat_(const MatCommaInitializer_<_Tp>& commaInitializer);
21162148

2149+
#ifdef CV_CXX_STD_ARRAY
2150+
template <std::size_t _N> explicit Mat_(const std::array<_Tp, _N>& arr, bool copyData=false);
2151+
#endif
2152+
21172153
Mat_& operator = (const Mat& m);
21182154
Mat_& operator = (const Mat_& m);
21192155
//! set all the elements to s.
@@ -2207,6 +2243,12 @@ template<typename _Tp> class Mat_ : public Mat
22072243

22082244
//! conversion to vector.
22092245
operator std::vector<_Tp>() const;
2246+
2247+
#ifdef CV_CXX_STD_ARRAY
2248+
//! conversion to array.
2249+
template<std::size_t _N> operator std::array<_Tp, _N>() const;
2250+
#endif
2251+
22102252
//! conversion to Vec
22112253
template<int n> operator Vec<typename DataType<_Tp>::channel_type, n>() const;
22122254
//! conversion to Matx
@@ -2281,6 +2323,7 @@ class CV_EXPORTS UMat
22812323
UMat(const UMat& m, const std::vector<Range>& ranges);
22822324
//! builds matrix from std::vector with or without copying the data
22832325
template<typename _Tp> explicit UMat(const std::vector<_Tp>& vec, bool copyData=false);
2326+
22842327
//! builds matrix from cv::Vec; the data is copied by default
22852328
template<typename _Tp, int n> explicit UMat(const Vec<_Tp, n>& vec, bool copyData=true);
22862329
//! builds matrix from cv::Matx; the data is copied by default

modules/core/include/opencv2/core/mat.inl.hpp

Lines changed: 99 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -77,6 +77,16 @@ template<typename _Tp> inline
7777
_InputArray::_InputArray(const std::vector<_Tp>& vec)
7878
{ init(FIXED_TYPE + STD_VECTOR + DataType<_Tp>::type + ACCESS_READ, &vec); }
7979

80+
#ifdef CV_CXX_STD_ARRAY
81+
template<typename _Tp, std::size_t _N> inline
82+
_InputArray::_InputArray(const std::array<_Tp, _N>& arr)
83+
{ init(FIXED_TYPE + FIXED_SIZE + STD_ARRAY + DataType<_Tp>::type + ACCESS_READ, arr.data(), Size(1, _N)); }
84+
85+
template<std::size_t _N> inline
86+
_InputArray::_InputArray(const std::array<Mat, _N>& arr)
87+
{ init(STD_ARRAY_MAT + ACCESS_READ, arr.data(), Size(1, _N)); }
88+
#endif
89+
8090
inline
8191
_InputArray::_InputArray(const std::vector<bool>& vec)
8292
{ init(FIXED_TYPE + STD_BOOL_VECTOR + DataType<bool>::type + ACCESS_READ, &vec); }
@@ -133,7 +143,9 @@ inline bool _InputArray::isUMat() const { return kind() == _InputArray::UMAT; }
133143
inline bool _InputArray::isMatVector() const { return kind() == _InputArray::STD_VECTOR_MAT; }
134144
inline bool _InputArray::isUMatVector() const { return kind() == _InputArray::STD_VECTOR_UMAT; }
135145
inline bool _InputArray::isMatx() const { return kind() == _InputArray::MATX; }
136-
inline bool _InputArray::isVector() const { return kind() == _InputArray::STD_VECTOR || kind() == _InputArray::STD_BOOL_VECTOR; }
146+
inline bool _InputArray::isVector() const { return kind() == _InputArray::STD_VECTOR ||
147+
kind() == _InputArray::STD_BOOL_VECTOR ||
148+
kind() == _InputArray::STD_ARRAY; }
137149
inline bool _InputArray::isGpuMatVector() const { return kind() == _InputArray::STD_VECTOR_CUDA_GPU_MAT; }
138150

139151
////////////////////////////////////////////////////////////////////////////////////////
@@ -149,6 +161,16 @@ template<typename _Tp> inline
149161
_OutputArray::_OutputArray(std::vector<_Tp>& vec)
150162
{ init(FIXED_TYPE + STD_VECTOR + DataType<_Tp>::type + ACCESS_WRITE, &vec); }
151163

164+
#ifdef CV_CXX_STD_ARRAY
165+
template<typename _Tp, std::size_t _N> inline
166+
_OutputArray::_OutputArray(std::array<_Tp, _N>& arr)
167+
{ init(FIXED_TYPE + FIXED_SIZE + STD_ARRAY + DataType<_Tp>::type + ACCESS_WRITE, arr.data(), Size(1, _N)); }
168+
169+
template<std::size_t _N> inline
170+
_OutputArray::_OutputArray(std::array<Mat, _N>& arr)
171+
{ init(STD_ARRAY_MAT + ACCESS_WRITE, arr.data(), Size(1, _N)); }
172+
#endif
173+
152174
inline
153175
_OutputArray::_OutputArray(std::vector<bool>&)
154176
{ CV_Error(Error::StsUnsupportedFormat, "std::vector<bool> cannot be an output array\n"); }
@@ -177,6 +199,16 @@ template<typename _Tp> inline
177199
_OutputArray::_OutputArray(const std::vector<_Tp>& vec)
178200
{ init(FIXED_TYPE + FIXED_SIZE + STD_VECTOR + DataType<_Tp>::type + ACCESS_WRITE, &vec); }
179201

202+
#ifdef CV_CXX_STD_ARRAY
203+
template<typename _Tp, std::size_t _N> inline
204+
_OutputArray::_OutputArray(const std::array<_Tp, _N>& arr)
205+
{ init(FIXED_TYPE + FIXED_SIZE + STD_ARRAY + DataType<_Tp>::type + ACCESS_WRITE, arr.data(), Size(1, _N)); }
206+
207+
template<std::size_t _N> inline
208+
_OutputArray::_OutputArray(const std::array<Mat, _N>& arr)
209+
{ init(FIXED_SIZE + STD_ARRAY_MAT + ACCESS_WRITE, arr.data(), Size(1, _N)); }
210+
#endif
211+
180212
template<typename _Tp> inline
181213
_OutputArray::_OutputArray(const std::vector<std::vector<_Tp> >& vec)
182214
{ init(FIXED_TYPE + FIXED_SIZE + STD_VECTOR_VECTOR + DataType<_Tp>::type + ACCESS_WRITE, &vec); }
@@ -244,6 +276,16 @@ template<typename _Tp> inline
244276
_InputOutputArray::_InputOutputArray(std::vector<_Tp>& vec)
245277
{ init(FIXED_TYPE + STD_VECTOR + DataType<_Tp>::type + ACCESS_RW, &vec); }
246278

279+
#ifdef CV_CXX_STD_ARRAY
280+
template<typename _Tp, std::size_t _N> inline
281+
_InputOutputArray::_InputOutputArray(std::array<_Tp, _N>& arr)
282+
{ init(FIXED_TYPE + FIXED_SIZE + STD_ARRAY + DataType<_Tp>::type + ACCESS_RW, arr.data(), Size(1, _N)); }
283+
284+
template<std::size_t _N> inline
285+
_InputOutputArray::_InputOutputArray(std::array<Mat, _N>& arr)
286+
{ init(STD_ARRAY_MAT + ACCESS_RW, arr.data(), Size(1, _N)); }
287+
#endif
288+
247289
inline _InputOutputArray::_InputOutputArray(std::vector<bool>&)
248290
{ CV_Error(Error::StsUnsupportedFormat, "std::vector<bool> cannot be an input/output array\n"); }
249291

@@ -271,6 +313,16 @@ template<typename _Tp> inline
271313
_InputOutputArray::_InputOutputArray(const std::vector<_Tp>& vec)
272314
{ init(FIXED_TYPE + FIXED_SIZE + STD_VECTOR + DataType<_Tp>::type + ACCESS_RW, &vec); }
273315

316+
#ifdef CV_CXX_STD_ARRAY
317+
template<typename _Tp, std::size_t _N> inline
318+
_InputOutputArray::_InputOutputArray(const std::array<_Tp, _N>& arr)
319+
{ init(FIXED_TYPE + FIXED_SIZE + STD_ARRAY + DataType<_Tp>::type + ACCESS_RW, arr.data(), Size(1, _N)); }
320+
321+
template<std::size_t _N> inline
322+
_InputOutputArray::_InputOutputArray(const std::array<Mat, _N>& arr)
323+
{ init(FIXED_SIZE + STD_ARRAY_MAT + ACCESS_RW, arr.data(), Size(1, _N)); }
324+
#endif
325+
274326
template<typename _Tp> inline
275327
_InputOutputArray::_InputOutputArray(const std::vector<std::vector<_Tp> >& vec)
276328
{ init(FIXED_TYPE + FIXED_SIZE + STD_VECTOR_VECTOR + DataType<_Tp>::type + ACCESS_RW, &vec); }
@@ -505,6 +557,25 @@ Mat::Mat(const std::vector<_Tp>& vec, bool copyData)
505557
Mat((int)vec.size(), 1, DataType<_Tp>::type, (uchar*)&vec[0]).copyTo(*this);
506558
}
507559

560+
#ifdef CV_CXX_STD_ARRAY
561+
template<typename _Tp, std::size_t _N> inline
562+
Mat::Mat(const std::array<_Tp, _N>& arr, bool copyData)
563+
: flags(MAGIC_VAL | DataType<_Tp>::type | CV_MAT_CONT_FLAG), dims(2), rows((int)arr.size()),
564+
cols(1), data(0), datastart(0), dataend(0), allocator(0), u(0), size(&rows)
565+
{
566+
if(arr.empty())
567+
return;
568+
if( !copyData )
569+
{
570+
step[0] = step[1] = sizeof(_Tp);
571+
datastart = data = (uchar*)arr.data();
572+
datalimit = dataend = datastart + rows * step[0];
573+
}
574+
else
575+
Mat((int)arr.size(), 1, DataType<_Tp>::type, (uchar*)arr.data()).copyTo(*this);
576+
}
577+
#endif
578+
508579
template<typename _Tp, int n> inline
509580
Mat::Mat(const Vec<_Tp, n>& vec, bool copyData)
510581
: flags(MAGIC_VAL | DataType<_Tp>::type | CV_MAT_CONT_FLAG), dims(2), rows(n), cols(1), data(0),
@@ -1114,6 +1185,16 @@ Mat::operator std::vector<_Tp>() const
11141185
return v;
11151186
}
11161187

1188+
#ifdef CV_CXX_STD_ARRAY
1189+
template<typename _Tp, std::size_t _N> inline
1190+
Mat::operator std::array<_Tp, _N>() const
1191+
{
1192+
std::array<_Tp, _N> v;
1193+
copyTo(v);
1194+
return v;
1195+
}
1196+
#endif
1197+
11171198
template<typename _Tp, int n> inline
11181199
Mat::operator Vec<_Tp, n>() const
11191200
{
@@ -1468,6 +1549,13 @@ Mat_<_Tp>::Mat_(const std::vector<_Tp>& vec, bool copyData)
14681549
: Mat(vec, copyData)
14691550
{}
14701551

1552+
#ifdef CV_CXX_STD_ARRAY
1553+
template<typename _Tp> template<std::size_t _N> inline
1554+
Mat_<_Tp>::Mat_(const std::array<_Tp, _N>& arr, bool copyData)
1555+
: Mat(arr, copyData)
1556+
{}
1557+
#endif
1558+
14711559
template<typename _Tp> inline
14721560
Mat_<_Tp>& Mat_<_Tp>::operator = (const Mat& m)
14731561
{
@@ -1745,6 +1833,16 @@ Mat_<_Tp>::operator std::vector<_Tp>() const
17451833
return v;
17461834
}
17471835

1836+
#ifdef CV_CXX_STD_ARRAY
1837+
template<typename _Tp> template<std::size_t _N> inline
1838+
Mat_<_Tp>::operator std::array<_Tp, _N>() const
1839+
{
1840+
std::array<_Tp, _N> a;
1841+
copyTo(a);
1842+
return a;
1843+
}
1844+
#endif
1845+
17481846
template<typename _Tp> template<int n> inline
17491847
Mat_<_Tp>::operator Vec<typename DataType<_Tp>::channel_type, n>() const
17501848
{
@@ -3426,7 +3524,6 @@ cols(1), allocator(0), usageFlags(USAGE_DEFAULT), u(0), offset(0), size(&rows)
34263524
Mat((int)vec.size(), 1, DataType<_Tp>::type, (uchar*)&vec[0]).copyTo(*this);
34273525
}
34283526

3429-
34303527
inline
34313528
UMat& UMat::operator = (const UMat& m)
34323529
{

modules/core/src/convert.cpp

Lines changed: 4 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -637,9 +637,11 @@ void cv::mixChannels(InputArrayOfArrays src, InputOutputArrayOfArrays dst,
637637
ocl_mixChannels(src, dst, fromTo, npairs))
638638

639639
bool src_is_mat = src.kind() != _InputArray::STD_VECTOR_MAT &&
640+
src.kind() != _InputArray::STD_ARRAY_MAT &&
640641
src.kind() != _InputArray::STD_VECTOR_VECTOR &&
641642
src.kind() != _InputArray::STD_VECTOR_UMAT;
642643
bool dst_is_mat = dst.kind() != _InputArray::STD_VECTOR_MAT &&
644+
dst.kind() != _InputArray::STD_ARRAY_MAT &&
643645
dst.kind() != _InputArray::STD_VECTOR_VECTOR &&
644646
dst.kind() != _InputArray::STD_VECTOR_UMAT;
645647
int i;
@@ -668,9 +670,11 @@ void cv::mixChannels(InputArrayOfArrays src, InputOutputArrayOfArrays dst,
668670
ocl_mixChannels(src, dst, &fromTo[0], fromTo.size()>>1))
669671

670672
bool src_is_mat = src.kind() != _InputArray::STD_VECTOR_MAT &&
673+
src.kind() != _InputArray::STD_ARRAY_MAT &&
671674
src.kind() != _InputArray::STD_VECTOR_VECTOR &&
672675
src.kind() != _InputArray::STD_VECTOR_UMAT;
673676
bool dst_is_mat = dst.kind() != _InputArray::STD_VECTOR_MAT &&
677+
dst.kind() != _InputArray::STD_ARRAY_MAT &&
674678
dst.kind() != _InputArray::STD_VECTOR_VECTOR &&
675679
dst.kind() != _InputArray::STD_VECTOR_UMAT;
676680
int i;

modules/core/src/lda.cpp

Lines changed: 3 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -53,7 +53,8 @@ static Mat argsort(InputArray _src, bool ascending=true)
5353

5454
static Mat asRowMatrix(InputArrayOfArrays src, int rtype, double alpha=1, double beta=0) {
5555
// make sure the input data is a vector of matrices or vector of vector
56-
if(src.kind() != _InputArray::STD_VECTOR_MAT && src.kind() != _InputArray::STD_VECTOR_VECTOR) {
56+
if(src.kind() != _InputArray::STD_VECTOR_MAT && src.kind() != _InputArray::STD_ARRAY_MAT &&
57+
src.kind() != _InputArray::STD_VECTOR_VECTOR) {
5758
String error_message = "The data is expected as InputArray::STD_VECTOR_MAT (a std::vector<Mat>) or _InputArray::STD_VECTOR_VECTOR (a std::vector< std::vector<...> >).";
5859
CV_Error(Error::StsBadArg, error_message);
5960
}
@@ -1096,6 +1097,7 @@ void LDA::lda(InputArrayOfArrays _src, InputArray _lbls) {
10961097
void LDA::compute(InputArrayOfArrays _src, InputArray _lbls) {
10971098
switch(_src.kind()) {
10981099
case _InputArray::STD_VECTOR_MAT:
1100+
case _InputArray::STD_ARRAY_MAT:
10991101
lda(asRowMatrix(_src, CV_64FC1), _lbls);
11001102
break;
11011103
case _InputArray::MAT:

modules/core/src/matmul.cpp

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -2579,7 +2579,7 @@ void cv::calcCovarMatrix( InputArray _src, OutputArray _covar, InputOutputArray
25792579
{
25802580
CV_INSTRUMENT_REGION()
25812581

2582-
if(_src.kind() == _InputArray::STD_VECTOR_MAT)
2582+
if(_src.kind() == _InputArray::STD_VECTOR_MAT || _src.kind() == _InputArray::STD_ARRAY_MAT)
25832583
{
25842584
std::vector<cv::Mat> src;
25852585
_src.getMatVector(src);

0 commit comments

Comments
 (0)