itom 1.0.14
|
00001 /* ******************************************************************** 00002 itom software 00003 URL: http://www.uni-stuttgart.de/ito 00004 Copyright (C) 2013, Institut für Technische Optik (ITO), 00005 Universität Stuttgart, Germany 00006 00007 This file is part of itom and its software development toolkit (SDK). 00008 00009 itom is free software; you can redistribute it and/or modify it 00010 under the terms of the GNU Library General Public Licence as published by 00011 the Free Software Foundation; either version 2 of the Licence, or (at 00012 your option) any later version. 00013 00014 In addition, as a special exception, the Institut für Technische 00015 Optik (ITO) gives you certain additional rights. 00016 These rights are described in the ITO LGPL Exception version 1.0, 00017 which can be found in the file LGPL_EXCEPTION.txt in this package. 00018 00019 itom is distributed in the hope that it will be useful, but 00020 WITHOUT ANY WARRANTY; without even the implied warranty of 00021 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU Library 00022 General Public Licence for more details. 00023 00024 You should have received a copy of the GNU Library General Public License 00025 along with itom. If not, see <http://www.gnu.org/licenses/>. 00026 *********************************************************************** */ 00027 00028 #ifndef __DATAOBJH 00029 #define __DATAOBJH 00030 00031 //#include <crtdbg.h> 00032 #include <cstdlib> 00033 #include <iostream> 00034 #include <complex> 00035 #include <limits> 00036 00037 #if !linux 00038 #pragma warning(disable:4996) 00039 #endif 00040 00041 #define NOMINMAX //see: http://social.msdn.microsoft.com/Forums/sv/vclanguage/thread/d986a370-d856-4f9e-9f14-53f3b18ab63e, this is only an issue with OpenCV 2.4.3, not 2.3.x 00042 00043 #include "opencv/cv.h" 00044 #include "opencv2/core/core.hpp" 00045 00046 #include "../common/sharedStructures.h" 00047 00048 #include "readWriteLock.h" 00049 00050 #include <vector> 00051 #include <map> 00052 #include <string> 00053 00054 namespace cv { 00055 00056 template<> inline ito::float32 saturate_cast<ito::float32>( ito::float64 v) 00057 { 00058 //return (float32)v; 00059 if(cvIsInf(v)) return std::numeric_limits<ito::float32>::infinity(); 00060 if(cvIsNaN(v)) return std::numeric_limits<ito::float32>::signaling_NaN(); 00061 return static_cast<ito::float32>(std::max ( (ito::float64)(- std::numeric_limits<ito::float32>::max()) , std::min ( v , (ito::float64) std::numeric_limits<ito::float32>::max() ))); 00062 } 00063 00064 template<> inline ito::float64 saturate_cast<ito::float64>( ito::float32 v) 00065 { 00066 //return (float64)v; 00067 if(cvIsInf(v)) return std::numeric_limits<ito::float64>::infinity(); 00068 if(cvIsNaN(v)) return std::numeric_limits<ito::float64>::signaling_NaN(); 00069 return static_cast<ito::float64>(v); 00070 } 00071 00072 template<typename _Tp> static inline _Tp saturate_cast(ito::complex128 /*v*/) { cv::error(cv::Exception(CV_StsAssert, "Not defined for input parameter type", "", __FILE__, __LINE__)); return 0; } 00073 template<typename _Tp> static inline _Tp saturate_cast(ito::complex64 /*v*/) { cv::error(cv::Exception(CV_StsAssert, "Not defined for input parameter type", "", __FILE__, __LINE__)); return 0; } 00074 00075 template<> inline ito::complex64 saturate_cast(ito::uint8 v){ return ito::complex64(static_cast<ito::float32>(v),0.0); } 00076 template<> inline ito::complex64 saturate_cast(ito::int8 v){ return ito::complex64(static_cast<ito::float32>(v),0.0); } 00077 template<> inline ito::complex64 saturate_cast(ito::uint16 v){ return ito::complex64(static_cast<ito::float32>(v),0.0); } 00078 template<> inline ito::complex64 saturate_cast(ito::int16 v){ return ito::complex64(static_cast<ito::float32>(v),0.0); } 00079 template<> inline ito::complex64 saturate_cast(ito::uint32 v){ return ito::complex64(static_cast<ito::float32>(v),0.0); } 00080 template<> inline ito::complex64 saturate_cast(ito::int32 v){ return ito::complex64(static_cast<ito::float32>(v),0.0); } 00081 template<> inline ito::complex64 saturate_cast(ito::float32 v){ return ito::complex64(v,0.0); } 00082 template<> inline ito::complex64 saturate_cast(ito::float64 v){ return ito::complex64(saturate_cast<ito::float32>(v),0.0); } 00083 template<> inline ito::complex64 saturate_cast(ito::complex64 v){ return v; } 00084 template<> inline ito::complex64 saturate_cast(ito::complex128 v){ return std::complex<ito::float32>(saturate_cast<ito::float32>(v.real()),saturate_cast<ito::float32>(v.imag())); } 00085 00086 template<> inline ito::complex128 saturate_cast(ito::uint8 v){ return ito::complex128(static_cast<ito::float64>(v),0.0); } 00087 template<> inline ito::complex128 saturate_cast(ito::int8 v){ return ito::complex128(static_cast<ito::float64>(v),0.0); } 00088 template<> inline ito::complex128 saturate_cast(ito::uint16 v){ return ito::complex128(static_cast<ito::float64>(v),0.0); } 00089 template<> inline ito::complex128 saturate_cast(ito::int16 v){ return ito::complex128(static_cast<ito::float64>(v),0.0); } 00090 template<> inline ito::complex128 saturate_cast(ito::uint32 v){ return ito::complex128(static_cast<ito::float64>(v),0.0); } 00091 template<> inline ito::complex128 saturate_cast(ito::int32 v){ return ito::complex128(static_cast<ito::float64>(v),0.0); } 00092 template<> inline ito::complex128 saturate_cast(ito::float32 v){ return ito::complex128(saturate_cast<ito::float64>(v),0.0); } 00093 template<> inline ito::complex128 saturate_cast(ito::float64 v){ return ito::complex128(v,0.0); } 00094 template<> inline ito::complex128 saturate_cast(ito::complex64 v){ return ito::complex128(saturate_cast<ito::float64>(v.real()),saturate_cast<ito::float64>(v.imag())); } 00095 template<> inline ito::complex128 saturate_cast(ito::complex128 v){ return v; } 00096 00097 } // namespace cv 00098 00099 00100 namespace ito { 00101 00102 #define __ITODEBUG 1 00103 00104 class DObjIterator; // Forward declaration 00105 class DataObject; 00106 class Range; 00107 struct Scalar; 00108 class DataObjectTags; 00109 class DataObjectTagType; 00110 00111 //---------------------------------------------------------------------------------------------------------------------------------- 00116 class Range 00117 { 00118 public: 00119 Range() : start(0), end(0) {} 00120 Range(int _start, int _end) { _start < _end ? (end = _end, start = _start) : (start = _end, end = _start); } 00121 inline unsigned int size() const { return end - start; } 00122 inline bool empty() const { return (start == end); } 00123 static Range all() { return Range(INT_MIN, INT_MAX); } 00125 int start; 00126 int end; 00127 }; 00128 00129 //---------------------------------------------------------------------------------------------------------------------------------- 00130 class DataObjectTagType 00131 { 00132 private: 00133 double m_dVal; 00134 std::string m_strValue; 00135 int m_type; 00136 00137 public: 00139 DataObjectTagType() : m_dVal(0), m_strValue(""), m_type(DataObjectTagType::typeInvalid){}; 00140 DataObjectTagType(double dVal) : m_dVal(dVal), m_strValue(""), m_type(DataObjectTagType::typeDouble){}; 00141 DataObjectTagType(std::string strVal) : m_dVal(std::numeric_limits<double>::signaling_NaN()), m_strValue(strVal), m_type(DataObjectTagType::typeString){}; 00142 DataObjectTagType(const char* cVal) : m_dVal(std::numeric_limits<double>::signaling_NaN()), m_type(DataObjectTagType::typeString){ cVal == NULL ? m_strValue = "" : m_strValue = cVal;}; 00144 DataObjectTagType(const DataObjectTagType& copyConstr) : m_dVal(copyConstr.m_dVal), m_strValue(copyConstr.m_strValue), m_type(copyConstr.m_type){}; 00145 00146 DataObjectTagType & operator = (const DataObjectTagType rhs) 00147 { 00148 this->m_dVal = rhs.m_dVal; 00149 this->m_strValue = rhs.m_strValue; 00150 this->m_type = rhs.m_type; 00151 00152 return *this; 00153 } 00154 00155 enum tTagType 00156 { 00157 typeInvalid = 0x000000, 00158 typeDouble = 0x000008, 00159 typeString = 0x000020 00160 }; 00161 00162 inline int getType(void) const {return m_type;}; 00163 inline bool isValid(void) const { return (m_type == DataObjectTagType::typeInvalid) ? false: true;}; 00164 00170 inline double getVal_ToDouble(void) 00171 { 00172 if(m_type == DataObjectTagType::typeInvalid) 00173 { 00174 return std::numeric_limits<double>::signaling_NaN(); 00175 } 00176 else if(m_type == DataObjectTagType::typeDouble) 00177 { 00178 return m_dVal; 00179 } 00180 else 00181 { 00182 double dVal = std::numeric_limits<double>::signaling_NaN(); 00183 //dVal = atof(m_strValue.c_str()); //sometimes the result of that line has been arbitrary, therefore this conversion should fail. 00184 return dVal; 00185 } 00186 } 00187 00193 inline std::string getVal_ToString(void) 00194 { 00195 if(m_type == DataObjectTagType::typeInvalid) 00196 { 00197 return std::string(); 00198 } 00199 else if(m_type == DataObjectTagType::typeString) 00200 { 00201 return m_strValue; 00202 } 00203 else 00204 { 00205 if(cvIsNaN(m_dVal)) return std::string("NaN"); 00206 if(cvIsInf(m_dVal)) return std::string("Inf"); 00207 /*if(m_dVal == std::numeric_limits<double>::quiet_NaN()) return std::string("NaN"); 00208 if(m_dVal == std::numeric_limits<double>::signaling_NaN()) return std::string("NaN"); 00209 if(m_dVal == std::numeric_limits<double>::infinity()) return std::string("Inf");*/ 00210 00211 std::ostringstream strs; 00212 strs << m_dVal; 00213 00214 return strs.str(); 00215 } 00216 } 00217 }; 00218 00219 //---------------------------------------------------------------------------------------------------------------------------------- 00228 class DataObjectTags 00229 { 00230 private: 00231 //std::map<std::string,std::string> m_tags; /*!< map for tags with keyword (std::string) and value (std::string) */ 00232 std::map<std::string, DataObjectTagType> m_tags; 00234 std::vector<double> m_axisOffsets; 00235 std::vector<double> m_axisScales; 00236 std::vector<std::string> m_axisDescription; 00237 std::vector<std::string> m_axisUnit; 00238 double m_valueOffset; 00239 double m_valueScale; 00240 std::string m_valueDescription; 00241 std::string m_valueUnit; 00243 double m_rotMatrix[9]; 00245 friend class DataObject; 00246 00247 00248 public: 00250 DataObjectTags(unsigned int totalAxisNum) : m_valueOffset(0.0), m_valueScale(1.0), m_valueDescription(""), m_valueUnit("") 00251 { 00252 m_tags.clear(); 00253 m_axisOffsets.resize(totalAxisNum, 0.0); 00254 m_axisScales.resize(totalAxisNum, 1.0); 00255 m_axisDescription.resize(totalAxisNum, ""); 00256 m_axisUnit.resize(totalAxisNum, ""); 00257 m_valueUnit = std::string(); 00258 memset(m_rotMatrix, 0, sizeof(double)*9); 00259 m_rotMatrix[0] = 1; // r11 00260 m_rotMatrix[4] = 1; // r22 00261 m_rotMatrix[8] = 1; // r33 00262 } 00263 00265 ~DataObjectTags() 00266 { 00267 m_tags.clear(); 00268 m_axisOffsets.clear(); 00269 m_axisScales.clear(); 00270 m_axisDescription.clear(); 00271 m_axisUnit.clear(); 00272 } 00273 00275 DataObjectTags(const DataObjectTags& copyConstr) 00276 { 00277 m_tags = copyConstr.m_tags; 00278 m_axisOffsets = copyConstr.m_axisOffsets; 00279 m_axisScales = copyConstr.m_axisScales; 00280 m_axisDescription = copyConstr.m_axisDescription; 00281 m_axisUnit = copyConstr.m_axisUnit; 00282 m_valueOffset = copyConstr.m_valueOffset; 00283 m_valueScale = copyConstr.m_valueScale; 00284 m_valueDescription = copyConstr.m_valueDescription; 00285 m_valueUnit = copyConstr.m_valueUnit; 00286 memcpy(m_rotMatrix,copyConstr.m_rotMatrix, sizeof(double)*9); 00287 } 00288 00289 //friend class DataObjectTags; //I am my best friend (my own and only friend, and therefore my copy-constr has access to my friends members. nice.) 00290 00291 }; 00292 00293 //---------------------------------------------------------------------------------------------------------------------------------- 00294 00295 class DObjConstIterator 00296 { 00297 public: 00298 00300 DObjConstIterator(); 00302 DObjConstIterator(const DataObject* _dObj, int pos = 0); 00304 DObjConstIterator(const DObjConstIterator& it); 00305 00307 DObjConstIterator& operator = (const DObjConstIterator& it); 00309 uchar* operator *() const; 00311 uchar* operator [](int i) const; 00312 00314 DObjConstIterator& operator += (int ofs); 00316 DObjConstIterator& operator -= (int ofs); 00318 DObjConstIterator& operator --(); 00320 DObjConstIterator operator --(int); 00322 DObjConstIterator& operator ++(); 00324 DObjConstIterator operator ++(int); 00325 00326 bool operator == (const DObjConstIterator& dObjIt); 00327 bool operator != (const DObjConstIterator& dObjIt); 00328 bool operator < (const DObjConstIterator& dObjIt); 00329 bool operator > (const DObjConstIterator& dObjIt); 00330 bool operator <= (const DObjConstIterator& dObjIt); 00331 bool operator >= (const DObjConstIterator& dObjIt); 00332 00333 protected: 00334 void seekAbs(int ofs); 00335 void seekRel(int ofs); 00336 00337 const DataObject* dObj; 00338 bool planeContinuous; 00339 size_t elemSize; 00340 uchar* ptr; 00341 uchar* sliceStart; 00342 uchar* sliceEnd; 00343 int plane; 00344 }; 00345 00346 //---------------------------------------------------------------------------------------------------------------------------------- 00347 class DObjIterator : public DObjConstIterator 00348 { 00349 public: 00350 00352 DObjIterator(); 00354 DObjIterator(DataObject* _dObj, int pos = 0); 00356 DObjIterator(const DObjIterator& it); 00357 00359 DObjIterator& operator = (const DObjIterator& it); 00361 uchar* operator *(); 00363 uchar* operator [](int i); 00364 00366 DObjIterator& operator += (int ofs); 00368 DObjIterator& operator -= (int ofs); 00370 DObjIterator& operator --(); 00372 DObjIterator operator --(int); 00374 DObjIterator& operator ++(); 00376 DObjIterator operator ++(int); 00377 }; 00378 00379 //---------------------------------------------------------------------------------------------------------------------------------- 00380 class DataObject 00381 { 00382 private: 00383 00385 00399 //length(sizes) == length(steps) 00400 void createHeader(const unsigned char dimensions, const size_t *sizes, const size_t *steps, const size_t elemSize) 00401 { 00402 if(dimensions == 1) 00403 { 00404 cv::error(cv::Exception(CV_StsAssert, "number of dimensions must be at least 2", "", __FILE__, __LINE__)); 00405 } 00406 00407 m_dims = dimensions; 00408 00409 if(dimensions > 0) 00410 { 00411 00412 if (m_roi.m_p) 00413 { 00414 if (*(m_roi.m_p-1) != dimensions) 00415 { 00416 delete[] (m_roi.m_p - 1); 00417 00418 m_roi.m_p = new size_t [(dimensions + 1) + (dimensions + 1) + (dimensions + 1)]; 00419 m_osize.m_p = static_cast<size_t *>(m_roi.m_p + dimensions) + 1; 00420 m_osize.m_p[-1] = dimensions; 00421 m_size.m_p = static_cast<size_t *>(m_osize.m_p + dimensions) + 1; 00422 m_size.m_p[-1] = dimensions; 00423 m_roi.m_p = m_roi.m_p + 1; 00424 m_roi.m_p[-1] = dimensions; 00425 } 00426 } 00427 else 00428 { 00429 m_roi.m_p = new size_t [(dimensions + 1) + (dimensions + 1) + (dimensions + 1)]; 00430 m_osize.m_p = static_cast<size_t *>(m_roi.m_p + dimensions) + 1; 00431 m_osize.m_p[-1] = dimensions; 00432 m_size.m_p = static_cast<size_t *>(m_osize.m_p + dimensions) + 1; 00433 m_size.m_p[-1] = dimensions; 00434 m_roi.m_p = m_roi.m_p + 1; 00435 m_roi.m_p[-1] = dimensions; 00436 } 00437 00438 for (uchar n = 0 ; n < dimensions ; n++) 00439 { 00440 m_size.m_p[n] = sizes[n]; 00441 m_roi.m_p[n] = 0; 00442 00443 if(steps == NULL || n == 0) 00444 { 00445 m_osize.m_p[n] = sizes[n]; 00446 } 00447 else if(n == dimensions - 1) //last element 00448 { 00449 m_osize.m_p[n] = steps[n-1] / elemSize; 00450 } 00451 else /*if(n < dimensions -1)*/ 00452 { 00453 m_osize.m_p[n] = steps[n-1] / steps[n]; 00454 } 00455 } 00456 } 00457 } 00458 00460 00473 void createHeaderWithROI(const unsigned char dimensions, const size_t *sizes, const size_t *osizes = NULL, const size_t *roi = NULL) 00474 { 00475 if(dimensions == 1) 00476 { 00477 cv::error(cv::Exception(CV_StsAssert, "number of dimensions must be at least 2", "", __FILE__, __LINE__)); 00478 } 00479 00480 m_dims = dimensions; 00481 00482 if(dimensions > 0) 00483 { 00484 00485 if (m_roi.m_p) 00486 { 00487 if (*(m_roi.m_p-1) != dimensions) 00488 { 00489 delete[] (m_roi.m_p-1); 00490 00491 m_roi.m_p = new size_t [(dimensions + 1) + (dimensions + 1) + (dimensions + 1)]; 00492 m_osize.m_p = static_cast<size_t *>(m_roi.m_p + dimensions) + 1; 00493 m_osize.m_p[-1] = dimensions; 00494 m_size.m_p = static_cast<size_t *>(m_osize.m_p + dimensions) + 1; 00495 m_size.m_p[-1] = dimensions; 00496 m_roi.m_p = m_roi.m_p + 1; //move m_p pointer by one 00497 m_roi.m_p[-1] = dimensions; 00498 } 00499 } 00500 else 00501 { 00502 m_roi.m_p = new size_t [(dimensions + 1) + (dimensions + 1) + (dimensions + 1)]; 00503 m_osize.m_p = static_cast<size_t *>(m_roi.m_p + dimensions) + 1; 00504 m_osize.m_p[-1] = dimensions; 00505 m_size.m_p = static_cast<size_t *>(m_osize.m_p + dimensions) + 1; 00506 m_size.m_p[-1] = dimensions; 00507 m_roi.m_p = m_roi.m_p + 1; //move m_p pointer by one 00508 m_roi.m_p[-1] = dimensions; 00509 } 00510 00511 for (uchar n = 0; n < dimensions; n++) 00512 { 00513 m_size.m_p[n] = sizes[n]; 00514 00515 if (osizes) 00516 { 00517 m_osize.m_p[n] = osizes[n]; 00518 } 00519 else 00520 { 00521 m_osize.m_p[n] = sizes[n]; 00522 } 00523 00524 if (roi) 00525 { 00526 m_roi.m_p[n] = roi[n]; 00527 } 00528 else 00529 { 00530 m_roi.m_p[n] = 0; 00531 } 00532 } 00533 } 00534 } 00535 00536 void create(const unsigned char dimensions, const size_t *sizes, const int type, const unsigned char continuous, const uchar* continuousDataPtr = NULL, const size_t* steps = NULL); 00538 void create(const unsigned char dimensions, const size_t *sizes, const int type, const cv::Mat* planes, const unsigned int nrOfPlanes); 00539 00540 void freeData(void); 00542 void secureFreeData(void); 00546 //---------------------------------------------------------------------------------------------------------------------------------- 00547 ito::RetVal matNumToIdx(const size_t matNum, size_t *matIdx) const; 00548 00550 00558 inline ito::RetVal matIdxToNum(const unsigned int *matIdx, size_t *matNum) const 00559 { 00560 *matNum = 0; 00561 if (m_dims <= 2) 00562 { 00563 return 0; 00564 } 00565 00566 size_t planeSize = 1; 00567 00568 for (int n = m_dims - 3; n >= 0; n--) 00569 { 00570 #if __ITODEBUG 00571 if (((size_t)matIdx[n] + m_roi[n]) >= m_osize[n]) 00572 { 00573 cv::error(cv::Exception(CV_StsAssert, "Index out of bounds", "", __FILE__, __LINE__)); 00574 } 00575 #endif 00576 (*matNum) += ((size_t)matIdx[n] + m_roi[n]) * planeSize; //CAST_TODO 00577 planeSize *= m_osize[n]; 00578 } 00579 00580 return 0; 00581 } 00582 00583 struct MSize 00584 { 00585 inline MSize() : m_p(NULL) {} 00586 //inline MSize(size_t *_p, char *_transp) : m_p(_p) {} 00587 // Size operator()() const; 00588 inline size_t operator [] (const int dim) const 00589 { 00590 return m_p[dim]; //return the size value. this operator corresponds to the real data representation in memory 00591 }; 00592 // inline unsigned int& operator [](const int i) { return m_p[i]; }; 00593 inline operator const size_t * () const { return m_p; } 00594 bool operator == (const MSize& sz) const 00595 { 00596 if(m_p == NULL || sz.m_p == NULL) 00597 { 00598 return sz.m_p == m_p; 00599 } 00600 00601 size_t d = m_p[-1], dsz = sz.m_p[-1]; 00602 if( d != dsz ) 00603 return false; 00604 if( d == 2 ) 00605 { 00606 return m_p[0] == sz.m_p[0] && m_p[1] == sz.m_p[1]; 00607 } 00608 00609 for( size_t i = 0; i < d - 2; i++ ) 00610 { 00611 if( m_p[i] != sz.m_p[i] ) 00612 { 00613 return false; 00614 } 00615 } 00616 return (m_p[d - 2] == sz.m_p[d - 2]) && (m_p[d - 1] == sz.m_p[d - 1]); 00617 } 00618 00619 inline bool operator != (const MSize& sz) const { return !(*this == sz); } 00620 00621 size_t *m_p; 00622 }; 00623 00624 struct MROI 00625 { 00626 inline MROI() : m_p(NULL) {}; 00627 //inline MROI(size_t *_p, char *_transp) : m_p(_p), m_pTransp(_transp) {} 00628 inline size_t operator [] (const int dim) const 00629 { 00630 return m_p[dim]; //return the size value. this operator corresponds to the real data representation in memory 00631 } 00632 00633 // inline unsigned int operator () (unsigned char dim, unsigned char beginEnd) const { beginEnd > 0 ? beginEnd = 1 : beginEnd = 0; return m_p[dim + beginEnd]; }; 00634 // inline unsigned int & operator () (unsigned char dim, unsigned char beginEnd) { return m_p[dim + beginEnd]; }; 00635 bool operator == (const MROI & rroi) const 00636 { 00637 if(m_p == NULL || rroi.m_p == NULL) 00638 { 00639 return rroi.m_p == m_p; 00640 } 00641 00642 if (m_p[-1] != rroi.m_p[-1]) 00643 { 00644 return false; 00645 } 00646 00647 size_t d = m_p[-1]; 00648 for (size_t n = 0; n < d - 2; n++) 00649 { 00650 if (m_p[n] != rroi.m_p[n]) 00651 { 00652 return false; 00653 } 00654 } 00655 00656 return m_p[d - 2] == rroi.m_p[d - 2] && m_p[d - 1] == rroi.m_p[d - 1]; 00657 00658 } 00659 00660 size_t *m_p; 00661 }; 00662 00663 DataObject(const DataObject& dObj, bool transposed); 00666 char m_continuous; 00667 char m_owndata; 00668 int m_type; 00669 int *m_pRefCount; 00670 int m_dims; 00671 MSize m_osize; 00672 MROI m_roi; 00673 MSize m_size; 00674 // std::vector<int *> m_data; /*!< vector with references to each matrix-plane. Must be cast to cv::Mat_<"m_type"> */ 00675 int **m_data; 00676 ReadWriteLock *m_objSharedDataLock; 00677 DataObjectTags *m_pDataObjectTags; 00678 ReadWriteLock m_objHeaderLock; 00680 inline int mdata_realloc(const size_t size) 00681 { 00682 static size_t sizeofs = sizeof(size_t) / sizeof(int *); 00683 00684 if (m_data) 00685 { 00686 m_data = static_cast<int **>(realloc(m_data - sizeofs, size * sizeof(int *) + sizeof(size_t))); 00687 } 00688 else 00689 { 00690 size_t numBytes = size * sizeof(int *) + sizeof(size_t); 00691 m_data = static_cast<int **>(calloc(numBytes, 1)); 00692 memset( m_data, 0, numBytes ); 00693 } 00694 (*reinterpret_cast<size_t*>(m_data)) = size; 00695 m_data += sizeofs; 00696 return 0; 00697 } 00698 inline size_t mdata_size(void) const 00699 { 00700 static size_t sizeofs = sizeof(size_t) / sizeof(int *); 00701 if (!m_data) 00702 return 0; 00703 else 00704 return (*reinterpret_cast<size_t *>(m_data - sizeofs)); 00705 } 00706 inline int mdata_free() 00707 { 00708 static size_t sizeofs = sizeof(size_t) / sizeof(int *); 00709 if (m_data) 00710 { 00711 int **ptr = m_data - sizeofs; 00712 free(ptr); 00713 } 00714 m_data = NULL; 00715 return 0; 00716 } 00717 00718 //low-level, templated methods 00719 //most low-level methods are marked "friend" such that they can access private members of their data object parameters 00720 template<typename _Tp> friend RetVal CreateFunc(DataObject *dObj, const unsigned char dimensions, const size_t *sizes, const unsigned char continuous, const uchar* continuousDataPtr, const size_t* steps); 00721 template<typename _Tp> friend RetVal CreateFuncWithCVPlanes(DataObject *dObj, const unsigned char dimensions, const size_t *sizes, const cv::Mat* planes, const unsigned int nrOfPlanes); 00722 template<typename _Tp> friend RetVal FreeFunc(DataObject *dObj); 00723 template<typename _Tp> friend RetVal SecureFreeFunc(DataObject *dObj); 00724 template<typename _Tp> friend RetVal CopyToFunc(const DataObject &lhs, DataObject &rhs, unsigned char regionOnly); 00725 template<typename _Tp> friend RetVal ConvertToFunc(const DataObject &lhs, DataObject &rhs, const int type, const double alpha, const double beta); 00726 template<typename _Tp> friend RetVal AdjustROIFunc(DataObject *dObj, const int *lims); 00727 template<typename _Tp> friend RetVal MinMaxLocFunc(const DataObject &dObj, double *minVal, double *maxVal, size_t *minPos, size_t *maxPos); 00728 template<typename _Tp> friend RetVal AssignScalarFunc(const DataObject *src, const ito::tDataType type, const void *scalar); 00729 template<typename _Tp> friend RetVal MakeContinuousFunc(const DataObject &dObj, DataObject &resDObj); 00730 template<typename _Tp> friend RetVal EvaluateTransposeFlagFunc(DataObject *dObj); 00731 template<typename _Tp> friend RetVal CalcMinMaxValues(DataObject *lhs, double &result_min, double &result_max, const int cmplxSel = 0); 00732 00733 // more friends due to change of std::vector to int ** for m_data ... 00734 template<typename _Tp> friend RetVal GetRangeFunc(DataObject *dObj, const int dtop, const int dbottom, const int dleft, const int dright); 00735 template<typename _Tp> friend RetVal AdjustROIFunc(DataObject *dObj, int dtop, int dbottom, int dleft, int dright); 00736 00737 public: 00738 size_t seekMat(const size_t matNum, const size_t numMats) const; 00739 size_t seekMat(const size_t matNum) const; 00740 size_t calcNumMats(void) const; 00741 00742 // TAGSPACEFUNCTIONS 00743 00745 inline double getValueOffset() const 00746 { 00747 if(!m_pDataObjectTags) return 0.0; // default 00748 return m_pDataObjectTags->m_valueOffset; 00749 } 00750 00752 inline double getValueScale() const 00753 { 00754 if(!m_pDataObjectTags) return 1.0; // default 00755 return m_pDataObjectTags->m_valueScale; 00756 } 00757 00759 inline const std::string getValueUnit() const 00760 { 00761 if(!m_pDataObjectTags) return std::string(); //default 00762 return m_pDataObjectTags->m_valueUnit; 00763 } 00764 00766 inline std::string getValueDescription() const 00767 { 00768 if(!m_pDataObjectTags) return std::string(); //default 00769 return m_pDataObjectTags->m_valueDescription; 00770 } 00771 00773 inline double getAxisOffset(const int axisNum) const 00774 { 00775 if(axisNum < 0 || axisNum >= m_dims) 00776 { 00777 cv::error(cv::Exception(CV_StsError, "Parameter axisNum out of range." ,"", __FILE__, __LINE__)); 00778 } 00779 if(!m_pDataObjectTags) return 0.0; // default 00780 00781 return m_pDataObjectTags->m_axisOffsets[axisNum] - m_roi[axisNum]; 00782 } 00783 00785 inline double getAxisScale(const int axisNum) const 00786 { 00787 if(axisNum < 0 || axisNum >= m_dims) 00788 { 00789 cv::error(cv::Exception(CV_StsError, "Parameter axisNum out of range." ,"", __FILE__, __LINE__)); 00790 } 00791 if(!m_pDataObjectTags) return 1.0; // default 00792 00793 return m_pDataObjectTags->m_axisScales[axisNum]; 00794 } 00795 00797 inline const std::string getAxisUnit(const int axisNum, bool &validOperation) const 00798 { 00799 if(axisNum < 0 || axisNum >= m_dims) 00800 { 00801 validOperation = false; 00802 cv::error(cv::Exception(CV_StsError, "Parameter axisNum out of range." ,"", __FILE__, __LINE__)); 00803 } 00804 if(!m_pDataObjectTags) 00805 { 00806 validOperation = false; 00807 return std::string(); //error 00808 } 00809 validOperation = true; 00810 return m_pDataObjectTags->m_axisUnit[axisNum]; 00811 } 00812 00814 const inline std::string getAxisDescription(const int axisNum, bool &validOperation) const 00815 { 00816 if(axisNum < 0 || axisNum >= m_dims) 00817 { 00818 validOperation = false; 00819 cv::error(cv::Exception(CV_StsError, "Parameter axisNum out of range." ,"", __FILE__, __LINE__)); 00820 } 00821 if(!m_pDataObjectTags) 00822 { 00823 validOperation = false; 00824 return std::string(); //error 00825 } 00826 00827 validOperation = true; 00828 return m_pDataObjectTags->m_axisDescription[axisNum]; 00829 } 00830 00831 inline DataObjectTagType getTag(const std::string key, bool &validOperation) const 00832 { 00833 validOperation = false; 00834 if(!m_pDataObjectTags) 00835 { 00836 return DataObjectTagType(); //error 00837 } 00838 //std::map<std::string, std::string>::iterator it = m_pDataObjectTags->m_tags.find(key); 00839 std::map<std::string, DataObjectTagType>::iterator it = m_pDataObjectTags->m_tags.find(key); 00840 if(it != m_pDataObjectTags->m_tags.end()) 00841 { 00842 validOperation = true; 00843 return it->second; 00844 } 00845 return DataObjectTagType(); 00846 } 00847 00849 //inline bool getTagByIndex(const int tagNumber, std::string &key, std::string &value) const 00850 inline bool getTagByIndex(const int tagNumber, std::string &key, DataObjectTagType &value) const 00851 { 00852 if(!m_pDataObjectTags) 00853 { 00854 key = std::string(); 00855 value = std::string(); 00856 return false; 00857 } 00858 00859 if((tagNumber < 0) || ((size_t)(tagNumber + 1) > m_pDataObjectTags->m_tags.size())) 00860 { 00861 key = std::string(); 00862 value = std::string(); 00863 return false; 00864 } 00865 //std::map<std::string,std::string>::iterator it = m_pDataObjectTags->m_tags.begin(); 00866 std::map<std::string, DataObjectTagType>::iterator it = m_pDataObjectTags->m_tags.begin(); 00867 for(int i = 0; i < tagNumber; i++) 00868 { 00869 it++; 00870 } 00871 00872 key = (*it).first; 00873 value = (*it).second; 00874 return true; 00875 } 00876 00878 inline std::string getTagKey(const int tagNumber, bool &validOperation) const 00879 { 00880 if(!m_pDataObjectTags) 00881 { 00882 validOperation = false; 00883 return std::string(""); //error 00884 } 00885 if((tagNumber < 0) || ((size_t)(tagNumber + 1) > m_pDataObjectTags->m_tags.size())) 00886 { 00887 validOperation = false; 00888 return std::string(""); //does not exist 00889 } 00890 //std::map<std::string,std::string>::iterator it = m_pDataObjectTags->m_tags.begin(); 00891 std::map<std::string, DataObjectTagType>::iterator it = m_pDataObjectTags->m_tags.begin(); 00892 validOperation = true; 00893 for(int i = 0; i < tagNumber; i++) 00894 { 00895 it++; 00896 } 00897 return (*it).first; 00898 } 00899 00901 inline int getTagListSize() const 00902 { 00903 if(!m_pDataObjectTags) return 0; //error 00904 return static_cast<int>(m_pDataObjectTags->m_tags.size()); 00905 } 00906 00907 // inline void setValueOffset(double offset) { m_valueOffset =offset; } 00908 // inline void setValueScale(double scale) { m_valueScale =scale; } 00909 00911 inline int setValueUnit(const std::string &unit) 00912 { 00913 if(!m_pDataObjectTags) return 1; //error 00914 m_pDataObjectTags->m_valueUnit = unit; 00915 return 0; 00916 } 00917 00919 inline int setValueDescription(const std::string &description) 00920 { 00921 if(!m_pDataObjectTags) return 1; //error 00922 m_pDataObjectTags->m_valueDescription = description; 00923 return 0; 00924 } 00925 00926 //inline lead to a linker error on MSVC when calling from several methods 00927 int setAxisOffset(const unsigned int axisNum, const double offset); 00928 int setAxisScale(const unsigned int axisNum, const double scale); 00929 int setAxisUnit(const unsigned int axisNum, const std::string &unit); 00930 int setAxisDescription(const unsigned int axisNum, const std::string &description); 00931 int setTag(const std::string &key, const DataObjectTagType &value); 00932 bool existTag(const std::string &key) const; 00933 bool deleteTag(const std::string &key); 00934 bool deleteAllTags(); 00935 int addToProtocol(const std::string &value); 00936 00937 00948 inline double getPhysToPix(const unsigned int dim, const double phys, bool &isInsideImage) const 00949 { 00950 double tPx = 0.0; 00951 if(static_cast<int>(dim) >= m_dims) 00952 { 00953 if(phys == 0.0) 00954 { 00955 isInsideImage = true; 00956 } 00957 else 00958 { 00959 isInsideImage = false; 00960 } 00961 return 0.0; 00962 } 00963 00964 if(m_pDataObjectTags) 00965 { 00966 tPx = (phys / getAxisScale(dim) + getAxisOffset(dim)); 00967 } 00968 else 00969 { 00970 tPx = phys; 00971 } 00972 00973 if(tPx > getSize(dim) - 1) 00974 { 00975 isInsideImage = false; 00976 tPx = static_cast<double>(getSize(dim)- 1); 00977 } 00978 else if( tPx < 0) 00979 { 00980 isInsideImage = false; 00981 tPx = 0; 00982 } 00983 else 00984 { 00985 isInsideImage = true; 00986 } 00987 00988 return tPx; 00989 } 00990 00994 inline int getPhysToPix2D(const double physY, double &tPxY, bool &isInsideImageY, const double physX, double &tPxX, bool &isInsideImageX) const 00995 { 00996 if(m_dims < 2) 00997 { 00998 tPxY = physY; 00999 if(physY != 0.0) 01000 { 01001 isInsideImageY = false; 01002 } 01003 01004 if(m_pDataObjectTags) 01005 { 01006 tPxX = physX / m_pDataObjectTags->m_axisScales[0] + m_pDataObjectTags->m_axisOffsets[0]; 01007 } 01008 else 01009 { 01010 tPxX = physX; 01011 } 01012 01013 if(tPxX > m_size[0] - 1) 01014 { 01015 isInsideImageX = false; 01016 tPxX = static_cast<double>(m_size[0] - 1); 01017 } 01018 } 01019 else 01020 { 01021 if(m_pDataObjectTags) 01022 { 01023 tPxX = physX / m_pDataObjectTags->m_axisScales[m_dims - 1] + m_pDataObjectTags->m_axisOffsets[m_dims - 1]; 01024 tPxY = physY / m_pDataObjectTags->m_axisScales[m_dims - 2] + m_pDataObjectTags->m_axisOffsets[m_dims - 2]; 01025 } 01026 else 01027 { 01028 tPxX = physX; 01029 tPxY = physY; 01030 } 01031 01032 if(tPxY > m_size[m_dims - 2] - 1) 01033 { 01034 isInsideImageY = false; 01035 tPxY = static_cast<double>(m_size[m_dims - 2] - 1); 01036 } 01037 if(tPxX > m_size[m_dims - 1] - 1) 01038 { 01039 isInsideImageX = false; 01040 tPxY = static_cast<double>(m_size[m_dims - 1] - 1); 01041 } 01042 } 01043 01044 if(tPxX < 0) 01045 { 01046 tPxX = 0; 01047 isInsideImageX = false; 01048 } 01049 if(tPxY < 0) 01050 { 01051 tPxY = 0; 01052 isInsideImageY = false; 01053 } 01054 return 0; 01055 } 01056 01066 inline double getPixToPhys(const unsigned int dim, const double pix, bool &isInsideImage) const 01067 { 01068 double tPhys = 0.0; 01069 if(static_cast<int>(dim) >= m_dims) 01070 { 01071 if(pix == 0) 01072 { 01073 isInsideImage = true; 01074 } 01075 else 01076 { 01077 isInsideImage = false; 01078 } 01079 return 0.0; 01080 } 01081 if(m_pDataObjectTags) 01082 { 01083 tPhys = (pix - getAxisOffset(dim)) * getAxisScale(dim); 01084 } 01085 else 01086 { 01087 tPhys = pix; 01088 } 01089 01090 if((pix > getSize(dim) - 1) || (pix < 0)) 01091 { 01092 isInsideImage = false; 01093 } 01094 else 01095 { 01096 isInsideImage = true; 01097 } 01098 01099 return tPhys; 01100 } 01101 01116 inline RetVal setXYRotationalMatrix(double r11, double r12, double r13, double r21, double r22, double r23, double r31, double r32, double r33) 01117 { 01118 if(!m_pDataObjectTags) return RetVal(retError, 0, "Tagspace not initialized"); // error 01119 m_pDataObjectTags->m_rotMatrix[0] = r11; 01120 m_pDataObjectTags->m_rotMatrix[1] = r12; 01121 m_pDataObjectTags->m_rotMatrix[2] = r13; 01122 m_pDataObjectTags->m_rotMatrix[3] = r21; 01123 m_pDataObjectTags->m_rotMatrix[4] = r22; 01124 m_pDataObjectTags->m_rotMatrix[5] = r23; 01125 m_pDataObjectTags->m_rotMatrix[6] = r31; 01126 m_pDataObjectTags->m_rotMatrix[7] = r32; 01127 m_pDataObjectTags->m_rotMatrix[8] = r33; 01128 return retOk; 01129 } 01130 01145 inline RetVal getXYRotationalMatrix(double &r11, double &r12, double &r13, double &r21, double &r22, double &r23, double &r31, double &r32, double &r33) const 01146 { 01147 if(!m_pDataObjectTags) return RetVal(retError, 0, "Tagspace not initialized"); // error 01148 r11 = m_pDataObjectTags->m_rotMatrix[0]; 01149 r12 = m_pDataObjectTags->m_rotMatrix[1]; 01150 r13 = m_pDataObjectTags->m_rotMatrix[2]; 01151 r21 = m_pDataObjectTags->m_rotMatrix[3]; 01152 r22 = m_pDataObjectTags->m_rotMatrix[4]; 01153 r23 = m_pDataObjectTags->m_rotMatrix[5]; 01154 r31 = m_pDataObjectTags->m_rotMatrix[6]; 01155 r32 = m_pDataObjectTags->m_rotMatrix[7]; 01156 r33 = m_pDataObjectTags->m_rotMatrix[8]; 01157 return retOk; 01158 } 01159 01160 RetVal copyTagMapTo(DataObject &rhs) const; 01161 RetVal copyAxisTagsTo(DataObject &rhs) const; 01163 // END TAGSPACE 01164 01166 inline int getDims(void) const { return m_dims; } 01167 01169 inline int getType(void) const { return m_type; } 01170 01172 inline char getContinuous(void) const { return m_continuous; } 01173 01175 inline char getOwnData(void) const { return m_owndata; } 01176 01178 01182 inline size_t getTotal() const 01183 { 01184 int dims = getDims(); 01185 size_t total = dims > 0 ? 1 : 0; 01186 for(int i = 0 ; i<dims ; i++) 01187 { 01188 total *= getSize(i); 01189 } 01190 return total; 01191 01192 } 01193 01195 01199 inline size_t getOriginalTotal() const 01200 { 01201 int dims = getDims(); 01202 size_t total = dims > 0 ? 1 : 0; 01203 for(int i = 0 ; i<dims ; i++) 01204 { 01205 total *= m_osize[i]; 01206 } 01207 return total; 01208 01209 } 01210 01212 01220 inline void lockRead() 01221 { 01222 m_objHeaderLock.lockRead(); 01223 if(m_objSharedDataLock) m_objSharedDataLock->lockRead(); 01224 } 01225 01227 01230 inline void lockWrite() 01231 { 01232 m_objHeaderLock.lockWrite(); 01233 if(m_objSharedDataLock) m_objSharedDataLock->lockWrite(); 01234 } 01235 01237 01240 inline void unlock() 01241 { 01242 if(m_objSharedDataLock) m_objSharedDataLock->unlock(); 01243 m_objHeaderLock.unlock(); 01244 } 01245 01246 RetVal copyTo(DataObject &rhs, unsigned char regionOnly = 0); 01247 RetVal convertTo(DataObject &rhs, const int type, const double alpha=1, const double beta=0 ) const; 01248 RetVal deepCopyPartial(DataObject &rhs); 01252 // std::vector<int *> get_mdata(void); 01253 int ** get_mdata(void); 01254 // std::vector<int *> get_mdata(void) const; 01255 int ** get_mdata(void) const; 01256 01258 01261 inline MSize getSize(void) { return m_size; } 01262 01264 01267 inline const MSize getSize(void) const { return m_size; } 01268 01270 01274 size_t getSize(int index) const 01275 { 01276 if(index < 0 || index >= m_dims) return -1; 01277 else 01278 { 01279 01280 return m_size[index]; 01281 } 01282 } 01283 01285 01289 size_t getOriginalSize(int index) const 01290 { 01291 if(index < 0 || index >= m_dims) return -1; 01292 else 01293 { 01294 01295 return m_osize[index]; 01296 } 01297 } 01298 01300 DObjIterator begin(); 01302 DObjIterator end(); 01303 01304 DObjConstIterator constBegin() const; 01305 DObjConstIterator constEnd() const; 01306 01307 01308 01309 01311 01314 DataObject(void) : m_continuous(1), m_owndata(1), m_type(0), m_pRefCount(0), m_dims(0), m_data(NULL), m_objSharedDataLock(0), m_pDataObjectTags(0) {} 01315 01317 01325 DataObject(const size_t size, const int type): m_continuous(1), m_owndata(1), m_pRefCount(0), m_dims(0), m_data(NULL), m_objSharedDataLock(0), m_pDataObjectTags(0) 01326 { 01327 size_t sizes[2] = {1, size}; 01328 this->create(2, sizes, type, 1); 01329 //DataObject(1, size, type); 01330 } 01331 01333 01341 DataObject(const size_t sizeY, const size_t sizeX, const int type): m_continuous(1), m_owndata(1), m_pRefCount(0), m_dims(0), m_data(NULL), m_objSharedDataLock(0), m_pDataObjectTags(0) 01342 { 01343 size_t sizes[2] = {sizeY, sizeX}; 01344 this->create(2, sizes, type, 1); 01345 } 01346 01348 01358 DataObject(const size_t sizeZ, const size_t sizeY, const size_t sizeX, const int type, const unsigned char continuous = 0) : m_continuous(continuous), m_owndata(1), m_pRefCount(0), m_dims(0), m_data(NULL), m_objSharedDataLock(0), m_pDataObjectTags(0) 01359 { 01360 size_t sizes[3] = {sizeZ, sizeY, sizeX}; 01361 01362 this->create(3, sizes, type, m_continuous); 01363 } 01364 01366 01380 DataObject(const size_t sizeZ, const size_t sizeY, const size_t sizeX, const int type, const uchar* continuousDataPtr, const size_t* steps = NULL) : m_continuous(1), m_owndata(1), m_pRefCount(0), m_dims(0), m_data(NULL), m_objSharedDataLock(0), m_pDataObjectTags(0) 01381 { 01382 size_t sizes[3] = {sizeZ, sizeY, sizeX}; 01383 01384 this->create(3, sizes, type, m_continuous, continuousDataPtr, steps); 01385 } 01386 01388 01397 DataObject(const unsigned char dimensions, const size_t *sizes, const int type, const unsigned char continuous = 0) : m_continuous(continuous), m_owndata(1), m_pRefCount(0), m_dims(0), m_data(NULL), m_objSharedDataLock(0), m_pDataObjectTags(0) 01398 { 01399 this->create(dimensions, sizes, type, m_continuous); 01400 } 01401 01403 01416 DataObject(const unsigned char dimensions, const size_t *sizes, const int type, const uchar* continuousDataPtr, const size_t* steps = NULL) : m_continuous(1), m_owndata(1), m_pRefCount(0), m_dims(0), m_data(NULL), m_objSharedDataLock(0), m_pDataObjectTags(0) 01417 { 01418 this->create(dimensions, sizes, type, m_continuous, continuousDataPtr, steps); 01419 } 01420 01421 DataObject(const unsigned char dimensions, const size_t *sizes, const int type, const cv::Mat* planes, const unsigned int nrOfPlanes) : m_continuous(0), m_owndata(1), m_pRefCount(0), m_dims(0), m_data(NULL), m_objSharedDataLock(0), m_pDataObjectTags(0) 01422 { 01423 this->create(dimensions, sizes, type, planes, nrOfPlanes); 01424 } 01425 01426 DataObject(const DataObject& copyConstr); 01428 01429 01435 ~DataObject(void) 01436 { 01437 freeData(); 01438 } 01439 01441 DataObject & operator = (const cv::Mat &rhs); 01442 DataObject & operator = (const DataObject &rhs); 01443 DataObject & operator = (const int8 value); 01444 DataObject & operator = (const uint8 value); 01445 DataObject & operator = (const int16 value); 01446 DataObject & operator = (const uint16 value); 01447 DataObject & operator = (const int32 value); 01448 DataObject & operator = (const uint32 value); 01449 DataObject & operator = (const float32 value); 01450 DataObject & operator = (const float64 value); 01451 DataObject & operator = (const complex64 value); 01452 DataObject & operator = (const complex128 value); 01455 DataObject & operator += (const DataObject &rhs); 01456 DataObject & operator += (const float64 value); 01457 01458 DataObject operator + (const DataObject &rhs); 01459 DataObject operator + (const float64 value); 01460 01461 DataObject & operator -= (const DataObject &rhs); 01462 DataObject & operator -= (const float64 value); 01463 01464 DataObject operator - (const DataObject &rhs); 01465 DataObject operator - (const float64 value); 01466 01467 DataObject & operator *= (const DataObject &rhs); 01468 DataObject & operator *= (const float64 factor); 01469 01470 DataObject operator * (const DataObject &rhs); 01471 DataObject operator * (const float64 factor); 01472 01473 // Comparison Operators 01474 DataObject operator < (DataObject &rhs); 01475 DataObject operator > (DataObject &rhs); 01476 DataObject operator <= (DataObject &rhs); 01477 DataObject operator >= (DataObject &rhs); 01478 DataObject operator == (DataObject &rhs); 01479 DataObject operator != (DataObject &rhs); 01480 01481 01482 // bitshift operators 01483 DataObject operator << (const unsigned int shiftbit); 01484 DataObject & operator <<= (const unsigned int shiftbit); 01485 DataObject operator >> (const unsigned int shiftbit); 01486 DataObject & operator >>= (const unsigned int shiftbit); 01487 01488 // bitwise operators 01489 DataObject operator & (const DataObject & rhs); 01490 DataObject & operator &= (const DataObject & rhs); 01491 DataObject operator | (const DataObject & rhs); 01492 DataObject & operator |= (const DataObject & rhs); 01493 DataObject operator ^ (const DataObject & rhs); 01494 DataObject & operator ^= (const DataObject & rhs); 01495 01496 // allocates matrix with zero values 01497 RetVal zeros(const int type); 01498 RetVal zeros(const size_t size, const int type); 01499 RetVal zeros(const size_t sizeY, const size_t sizeX, const int type); 01500 RetVal zeros(const size_t sizeZ, const size_t sizeY, const size_t sizeX, const int type, const unsigned char continuous = 0); 01501 RetVal zeros(const unsigned char dimensions, const size_t *sizes, const int type, const unsigned char continuous = 0); 01502 01503 // allocates matrix with all values set to one 01504 RetVal ones(const int type); 01505 RetVal ones(const size_t size, const int type); 01506 RetVal ones(const size_t sizeY, const size_t sizeX, const int type); 01507 RetVal ones(const size_t sizeZ, const size_t sizeY, const size_t sizeX, const int type, const unsigned char continuous = 0); 01508 RetVal ones(const unsigned char dimensions, const size_t *sizes, const int type, const unsigned char continuous = 0); 01509 01510 // allocates matrix with uniform distributed noise 01511 RetVal rand(const int type, const bool randMode = false); 01512 RetVal rand(const size_t size, const int type, const bool randMode = false); 01513 RetVal rand(const size_t sizeY, const size_t sizeX, const int type, const bool randMode = false); 01514 RetVal rand(const size_t sizeZ, const size_t sizeY, const size_t sizeX, const int type, const bool randMode, const unsigned char continuous = 0); 01515 RetVal rand(const unsigned char dimensions, const size_t *sizes, const int type, const bool randMode, const unsigned char continuous = 0); 01516 01517 // allocates matrix with eye-matrix representation 01518 RetVal eye(const int type); 01519 RetVal eye(const size_t size, const int type); 01520 01521 RetVal conj(); 01522 DataObject adj() const; 01523 DataObject trans() const; 01524 01525 //RetVal makeContinuous(void); 01526 01527 DataObject mul(const DataObject &mat2, const double scale = 1.0); 01528 DataObject div(const DataObject &mat2, const double scale = 1.0); 01529 01530 DataObject squeeze() const; 01531 01532 size_t elemSize() const; 01533 01534 /* 01535 // Adressing operators () 01536 // You should NOT use DataObject::operator here! Otherwise the MsVc compiler will hate you - at least today: 30.03.2011 01537 template<typename _Tp> _Tp& operator () (const unsigned int x) const; 01538 template<typename _Tp> _Tp& operator () (const unsigned int x); 01539 template<typename _Tp> _Tp& operator () (const unsigned int y, const unsigned int x) const; 01540 template<typename _Tp> _Tp& operator () (const unsigned int y, const unsigned int x); 01541 template<typename _Tp> _Tp& operator () (const unsigned int z, const unsigned int y, const unsigned int x) const; 01542 template<typename _Tp> _Tp& operator () (const unsigned int z, const unsigned int y, const unsigned int x); 01543 template<typename _Tp> _Tp& operator () (const unsigned int *idx) const; 01544 template<typename _Tp> _Tp& operator () (const unsigned int *idx); 01545 DataObject operator () (const ito::Range rowRange, const ito::Range colRange); 01546 DataObject operator () (ito::Range *ranges); 01547 01548 */ 01549 // Adressing functions 01550 01552 01556 template<typename _Tp> _Tp& at(const int x) const 01557 { 01558 #if __ITODEBUG 01559 if ((m_dims != 1) && !((m_dims == 2) && ((m_size[0] == 1) || (m_size[1] == 1)))) 01560 { 01561 cv::error(cv::Exception(CV_StsAssert, "Dimension mismatch while addressing data field", "", __FILE__, __LINE__)); 01562 } 01563 #endif 01564 if (m_dims == 1) 01565 { 01566 #if __ITODEBUG 01567 if ((size_t)x >= m_size[0]) 01568 { 01569 cv::error(cv::Exception(CV_StsAssert, "Index out of bounds", "", __FILE__, __LINE__)); 01570 } 01571 #endif 01572 return (*(cv::Mat_<_Tp> *)(m_data[0]))(0, x); 01573 } 01574 else if (m_size[0] == 1) 01575 { 01576 #if __ITODEBUG 01577 if ((size_t)x >= m_size[1]) 01578 { 01579 cv::error(cv::Exception(CV_StsAssert, "Index out of bounds", "", __FILE__, __LINE__)); 01580 } 01581 #endif 01582 return (*(cv::Mat_<_Tp> *)(m_data[0]))(0, x); 01583 } 01584 else 01585 { 01586 #if __ITODEBUG 01587 if ((size_t)x >= m_size[0]) 01588 { 01589 cv::error(cv::Exception(CV_StsAssert, "Index out of bounds", "", __FILE__, __LINE__)); 01590 } 01591 #endif 01592 return (*(cv::Mat_<_Tp> *)(m_data[0]))(x, 0); 01593 } 01594 } 01595 01597 01601 template<typename _Tp> _Tp& at(const int x) 01602 { 01603 #if __ITODEBUG 01604 if ((m_dims != 1) && !((m_dims == 2) && ((m_size[0] == 1) || (m_size[1] == 1)))) 01605 { 01606 cv::error(cv::Exception(CV_StsAssert, "Dimension mismatch while addressing data field", "", __FILE__, __LINE__)); 01607 } 01608 #endif 01609 if (m_dims == 1) 01610 { 01611 #if __ITODEBUG 01612 if ((size_t)x >= m_size[0]) 01613 { 01614 cv::error(cv::Exception(CV_StsAssert, "Index out of bounds", "", __FILE__, __LINE__)); 01615 } 01616 #endif 01617 return (*(cv::Mat_<_Tp> *)(m_data[0]))(0, x); 01618 } 01619 else if (m_size[0] == 1) 01620 { 01621 #if __ITODEBUG 01622 if ((size_t)x >= m_size[1]) 01623 { 01624 cv::error(cv::Exception(CV_StsAssert, "Index out of bounds", "", __FILE__, __LINE__)); 01625 } 01626 #endif 01627 return (*(cv::Mat_<_Tp> *)(m_data[0]))(0, x); 01628 } 01629 else 01630 { 01631 #if __ITODEBUG 01632 if ((size_t)x >= m_size[0]) 01633 { 01634 cv::error(cv::Exception(CV_StsAssert, "Index out of bounds", "", __FILE__, __LINE__)); 01635 } 01636 #endif 01637 return (*(cv::Mat_<_Tp> *)(m_data[0]))(x, 0); 01638 } 01639 } 01640 01642 01647 template<typename _Tp> _Tp& at(const unsigned int y, const unsigned int x) const 01648 { 01649 #if __ITODEBUG 01650 if (m_dims != 2) 01651 { 01652 cv::error(cv::Exception(CV_StsAssert, "Dimension mismatch while addressing data field", "", __FILE__, __LINE__)); 01653 } 01654 else if ((x >= m_size[1]) || (y >= m_size[0]) ) 01655 { 01656 cv::error(cv::Exception(CV_StsAssert, "Index out of bounds", "", __FILE__ , __LINE__)); 01657 } 01658 #endif 01659 return (*(cv::Mat_<_Tp> *)(m_data[0]))(y, x); 01660 } 01661 01663 01668 template<typename _Tp> _Tp& at(const unsigned int y, const unsigned int x) 01669 { 01670 #if __ITODEBUG 01671 if (m_dims != 2) 01672 { 01673 cv::error(cv::Exception(CV_StsAssert, "Dimension mismatch while addressing data field", "", __FILE__, __LINE__)); 01674 } 01675 else if (((size_t)x >= m_size[1]) || ((size_t)y >= m_size[0]) ) 01676 { 01677 cv::error(cv::Exception(CV_StsAssert, "Index out of bounds", "", __FILE__ , __LINE__)); 01678 } 01679 01680 #endif 01681 return (*(cv::Mat_<_Tp> *)(m_data[0]))(y, x); 01682 } 01683 01685 01691 template<typename _Tp> _Tp& at(const unsigned int z, const unsigned int y, const unsigned int x) const 01692 { 01693 #if __ITODEBUG 01694 if (m_dims != 3) 01695 { 01696 cv::error(cv::Exception(CV_StsAssert, "Dimension mismatch while addressing data field", "", __FILE__, __LINE__)); 01697 } 01698 else if (((size_t)x >= m_size[2]) || ((size_t)y >= m_size[1]) || (((size_t)z + m_roi[0]) >= (m_roi[0] + m_size[0]))) 01699 { 01700 cv::error(cv::Exception(CV_StsAssert, "Index out of bounds", "", __FILE__ , __LINE__)); 01701 } 01702 #endif 01703 01704 return (*(cv::Mat_<_Tp> *)(m_data[z + m_roi[0]]))(y, x); 01705 } 01706 01708 01714 template<typename _Tp> _Tp& at(const unsigned int z, const unsigned int y, const unsigned int x) 01715 { 01716 #if __ITODEBUG 01717 if (m_dims != 3) 01718 { 01719 cv::error(cv::Exception(CV_StsAssert, "Dimension mismatch while addressing data field", "", __FILE__, __LINE__)); 01720 } 01721 else if (((size_t)x >= m_size[2]) || ((size_t)y >= m_size[1]) || (((size_t)z + m_roi[0]) >= (m_roi[0] + m_size[0]))) 01722 { 01723 cv::error(cv::Exception(CV_StsAssert, "Index out of bounds", "", __FILE__ , __LINE__)); 01724 } 01725 #endif 01726 return (*(cv::Mat_<_Tp> *)(m_data[z + m_roi[0]]))(y, x); 01727 } 01728 01730 01735 template<typename _Tp> _Tp& at(const unsigned int *idx) const //idx is in virtual order 01736 { 01737 size_t matNum = 0; 01738 01739 matIdxToNum(idx, &matNum); 01740 01741 return (*(cv::Mat_<_Tp> *)(m_data[matNum]))(idx[m_dims - 2], idx[m_dims - 1]); 01742 } 01743 01745 01750 template<typename _Tp> _Tp& at(const unsigned int *idx) //idx is in virtual order 01751 { 01752 size_t matNum = 0; 01753 01754 matIdxToNum(idx, &matNum); 01755 01756 return (*(cv::Mat_<_Tp> *)(m_data[matNum]))(idx[m_dims - 2], idx[m_dims - 1]); 01757 } 01758 01759 DataObject at(const ito::Range rowRange, const ito::Range colRange); 01760 DataObject at(ito::Range *ranges); 01762 01763 01769 uchar* rowPtr(const size_t matNum, const int y) 01770 { 01771 size_t matIndex = seekMat(matNum); 01772 return ((cv::Mat*)m_data[matIndex])->ptr(y); 01773 } 01774 01776 01782 const uchar* rowPtr(const size_t matNum, const int y) const 01783 { 01784 size_t matIndex = seekMat(matNum); 01785 return ((cv::Mat*)m_data[matIndex])->ptr(y); 01786 } 01787 01788 DataObject row(const int selRow); 01789 DataObject col(const int selCol); 01790 //DataObject diag(void); 01791 01792 // ROI 01793 DataObject & adjustROI(const int dtop, const int dbottom, const int dleft, const int dright); 01794 DataObject & adjustROI(const unsigned char dims, const int *lims); 01795 RetVal locateROI(int *wholeSizes, int *offsets); 01796 RetVal locateROI(int *lims); 01797 template<typename _Tp> RetVal copyFromData2D(const _Tp* src, const size_t sizeX, const size_t sizeY); 01798 template<typename _Tp> RetVal copyFromData2D(const _Tp *src, const size_t sizeX, const size_t sizeY, const int x0, const int y0, const size_t width, const size_t height); 01799 template<typename _Tp> RetVal checkType(const _Tp *src); //compares type of elements in this data objects and type of given argument (doc in source) 01800 01801 // 01802 template<typename T2> operator T2 (); 01803 }; 01804 01805 01806 //---------------------------------------------------------------------------------------------------------------------------------- 01807 // functions for DataObject in namespace ITO, which are NOT member functions 01808 //---------------------------------------------------------------------------------------------------------------------------------- 01809 DataObject abs(const DataObject &dObj); 01810 DataObject arg(const DataObject &dObj); 01811 DataObject real(const DataObject &dObj); 01812 DataObject imag(const DataObject &dObj); 01814 DataObject makeContinuous(const DataObject &dObj); 01816 template<typename _Tp, typename _T2> RetVal CastFunc(const DataObject *dObj, DataObject *resObj, double alpha = 1.0, double beta = 0.0); 01817 01818 //RetVal minMaxLoc(const DataObject &dObj, double *minVal, double *maxVal, size_t *minPos = NULL, size_t *maxPos = NULL); 01819 01821 01828 template<typename _Tp> _Tp numberConversion(ito::tDataType fromType, void *scalar) 01829 { 01830 _Tp retValue = 0; 01831 01832 switch(fromType) 01833 { 01834 case ito::tUInt8: 01835 retValue = cv::saturate_cast<_Tp>(*(static_cast<uint8*>(scalar))); 01836 break; 01837 case ito::tInt8: 01838 retValue = cv::saturate_cast<_Tp>(*(static_cast<int8*>(scalar))); 01839 break; 01840 case ito::tUInt16: 01841 retValue = cv::saturate_cast<_Tp>(*(static_cast<uint16*>(scalar))); 01842 break; 01843 case ito::tInt16: 01844 retValue = cv::saturate_cast<_Tp>(*(static_cast<int16*>(scalar))); 01845 break; 01846 case ito::tUInt32: 01847 retValue = cv::saturate_cast<_Tp>(*(static_cast<uint32*>(scalar))); 01848 break; 01849 case ito::tInt32: 01850 retValue = cv::saturate_cast<_Tp>(*(static_cast<int32*>(scalar))); 01851 break; 01852 case ito::tFloat32: 01853 retValue = cv::saturate_cast<_Tp>(*(static_cast<ito::float32*>(scalar))); 01854 break; 01855 case ito::tFloat64: 01856 retValue = cv::saturate_cast<_Tp>(*(static_cast<ito::float64*>(scalar))); 01857 break; 01858 case ito::tComplex64: 01859 retValue = cv::saturate_cast<_Tp>(*(static_cast<ito::complex64*>(scalar))); 01860 break; 01861 case ito::tComplex128: 01862 retValue = cv::saturate_cast<_Tp>(*(static_cast<ito::complex128*>(scalar))); 01863 break; 01864 default: 01865 cv::error(cv::Exception(CV_StsAssert, "Input value type unkown", "", __FILE__, __LINE__)); 01866 retValue = 0; 01867 } 01868 01869 return retValue; 01870 }; 01871 01872 01873 01874 //---------------------------------------------------------------------------------------------------------------------------------- 01875 // cout 01876 //---------------------------------------------------------------------------------------------------------------------------------- 01877 template<typename _Tp> static std::ostream& coutFunc(std::ostream& out, const DataObject& dObj) 01878 { 01879 //cv::Mat_<_Tp> *cvMat = NULL; 01880 size_t numMats = dObj.calcNumMats(); 01881 size_t tMat = 0; 01882 01883 std::cout << "Array("; 01884 01885 for (size_t nMat = 0; nMat < numMats; nMat++) 01886 { 01887 tMat = dObj.seekMat(nMat, numMats); 01888 std::cout << tMat + 1 << "->("; 01889 01890 //#ifndef linux 01891 01892 std::cout << cv::format( (*((cv::Mat_<_Tp> *)((dObj.get_mdata())[tMat]))) , "numpy" ) << std::endl << std::endl; 01893 //#endif 01894 01895 std::cout << ")" << "\n" << std::endl; 01896 } 01897 std::cout << ")" << "\n" << std::endl; 01898 return out; 01899 01900 } 01901 01902 typedef std::ostream& (*tCoutFunc)(std::ostream& out, const DataObject& dObj); 01903 01904 static tCoutFunc fListCout[] = 01905 { 01906 coutFunc<int8>, 01907 coutFunc<uint8>, 01908 coutFunc<int16>, 01909 coutFunc<uint16>, 01910 coutFunc<int32>, 01911 coutFunc<uint32>, 01912 coutFunc<ito::float32>, 01913 coutFunc<ito::float64>, 01914 coutFunc<ito::complex64>, 01915 coutFunc<ito::complex128> 01916 }; 01917 01918 static inline std::ostream& operator << (std::ostream& out, const DataObject& dObj) 01919 { 01920 return fListCout[dObj.getType()](out, dObj); 01921 } 01922 01924 01931 static ito::tDataType convertCmplxTypeToRealType(ito::tDataType cmplxType) 01932 { 01933 switch(cmplxType) 01934 { 01935 case ito::tInt8: 01936 case ito::tUInt8: 01937 case ito::tInt16: 01938 case ito::tUInt16: 01939 case ito::tInt32: 01940 case ito::tUInt32: 01941 case ito::tFloat32: 01942 case ito::tFloat64: 01943 return cmplxType; 01944 case ito::tComplex64: 01945 return ito::tFloat32; 01946 case ito::tComplex128: 01947 return ito::tFloat64; 01948 } 01949 01950 cv::error(cv::Exception(CV_StsAssert, "Input data type unknown", "", __FILE__, __LINE__)); 01951 return ito::tInt8; 01952 } 01953 01955 01963 template<typename _Tp> static inline ito::tDataType getDataType(const _Tp* /*src*/) 01964 { 01965 cv::error(cv::Exception(CV_StsAssert, "Input value type unkown", "", __FILE__, __LINE__)); 01966 return ito::tInt8; 01967 } 01968 01969 template<> inline ito::tDataType getDataType(const uint8* /*src*/) { return ito::tUInt8; } 01970 template<> inline ito::tDataType getDataType(const int8* /*src*/) { return ito::tInt8; } 01971 template<> inline ito::tDataType getDataType(const uint16* /*src*/) { return ito::tUInt16; } 01972 template<> inline ito::tDataType getDataType(const int16* /*src*/) { return ito::tInt16; } 01973 template<> inline ito::tDataType getDataType(const uint32* /*src*/) { return ito::tUInt32; } 01974 template<> inline ito::tDataType getDataType(const int32* /*src*/) { return ito::tInt32; } 01975 template<> inline ito::tDataType getDataType(const float32* /*src*/) { return ito::tFloat32; } 01976 template<> inline ito::tDataType getDataType(const float64* /*src*/) { return ito::tFloat64; } 01977 template<> inline ito::tDataType getDataType(const complex64* /*src*/) { return ito::tComplex64; } 01978 template<> inline ito::tDataType getDataType(const complex128* /*src*/) { return ito::tComplex128; } 01979 01980 01982 01991 template<typename _Tp> static inline ito::tDataType getDataType2() 01992 { 01993 cv::error(cv::Exception(CV_StsAssert, "Input value type unkown", "", __FILE__, __LINE__)); 01994 return ito::tInt8; 01995 } 01996 01997 template<> inline ito::tDataType getDataType2<uint8*>() { return ito::tUInt8; } 01998 template<> inline ito::tDataType getDataType2<int8*>() { return ito::tInt8; } 01999 template<> inline ito::tDataType getDataType2<uint16*>() { return ito::tUInt16; } 02000 template<> inline ito::tDataType getDataType2<int16*>() { return ito::tInt16; } 02001 template<> inline ito::tDataType getDataType2<uint32*>() { return ito::tUInt32; } 02002 template<> inline ito::tDataType getDataType2<int32*>() { return ito::tInt32; } 02003 template<> inline ito::tDataType getDataType2<float32*>() { return ito::tFloat32; } 02004 template<> inline ito::tDataType getDataType2<float64*>() { return ito::tFloat64; } 02005 template<> inline ito::tDataType getDataType2<complex64*>() { return ito::tComplex64; } 02006 template<> inline ito::tDataType getDataType2<complex128*>() { return ito::tComplex128; } 02007 02008 02010 02020 template<typename _Tp> static inline bool isZeroValue(_Tp v, _Tp /*epsilon*/) 02021 { 02022 return v == 0; 02023 } 02024 template<> inline bool isZeroValue(float32 v, float32 epsilon) 02025 { 02026 return v >= epsilon ? false : (v <= -epsilon ? false : true); 02027 } 02028 template<> inline bool isZeroValue(float64 v, float64 epsilon) 02029 { 02030 return v >= epsilon ? false : (v <= -epsilon ? false : true); 02031 } 02032 template<> inline bool isZeroValue(std::complex<ito::float32> v, std::complex<ito::float32> epsilon) 02033 { 02034 return isZeroValue<ito::float32>(v.real(),epsilon.real()) && isZeroValue<ito::float32>(v.imag(),epsilon.real()); 02035 } 02036 template<> inline bool isZeroValue(std::complex<ito::float64> v, std::complex<ito::float64> epsilon) 02037 { 02038 return isZeroValue<ito::float64>(v.real(),epsilon.real()) && isZeroValue<ito::float64>(v.imag(),epsilon.real()); 02039 } 02040 02041 02042 02043 02044 02045 //---------------------------------------------------------------------------------------------------------------------------------- 02046 // friend functions to access private members of DataObject 02047 //---------------------------------------------------------------------------------------------------------------------------------- 02048 } //namespace ito 02049 02050 #endif //__DATAOBJH 02051 02052