ML Reference
MeVis/Foundation/Sources/ML/include/mlStdTypeInfos.h
Go to the documentation of this file.
00001 // **InsertLicense** code
00002 //-------------------------------------------------------------------------
00012 //-------------------------------------------------------------------------
00013 #ifndef __mlStdTypeInfos_H
00014 #define __mlStdTypeInfos_H
00015 
00016 // ML-includes
00017 #ifndef __mlInitSystemML_H
00018 #include "mlInitSystemML.h"
00019 #endif
00020 #ifndef __mlBasics_H
00021 #include "mlBasics.h"
00022 #endif
00023 
00024 #include "mlSystemWarningsDisable.h"
00025 #include <math.h>
00026 #include "mlSystemWarningsRestore.h"
00027 
00028 #ifdef _MSC_VER
00029 #pragma warning(push)
00030 // warning C4244: 'Argument': Konvertierung von 'typ1' in 'typ2', möglicher Datenverlust
00031 #pragma warning(disable: 4244)
00032 // warning C4127: Bedingter Ausdruck ist konstant
00033 #pragma warning(disable: 4127)
00034 #endif
00035 
00036 ML_START_NAMESPACE
00037 
00039 const MLint _ML_STD_SLEN=64;
00040 
00041 //--------------------------------------------------------------------------------------
00043 //--------------------------------------------------------------------------------------
00044 template <typename VTYP>
00045 class MLEXPORT MLTStdTypeInfos : public MLTypeInfos 
00046 {
00047   
00048 public:
00049   
00051 
00052   static inline const char *typeName(MLint8   *) { static const char name[]="int8";           return name; }
00053   static inline const char *typeName(MLuint8  *) { static const char name[]="unsigned int8";  return name; }
00054   static inline const char *typeName(MLint16  *) { static const char name[]="int16";          return name; }
00055   static inline const char *typeName(MLuint16 *) { static const char name[]="unsigned int16"; return name; }
00056   static inline const char *typeName(MLint32  *) { static const char name[]="int32";          return name; }
00057   static inline const char *typeName(MLuint32 *) { static const char name[]="unsigned int32"; return name; }
00058   static inline const char *typeName(MLfloat  *) { static const char name[]="float";          return name; }
00059   static inline const char *typeName(MLdouble *) { static const char name[]="double";         return name; }
00060   static inline const char *typeName(MLint64  *) { static const char name[]="int64";          return name; }
00061   static inline const char *typeName(MLuint64 *) { static const char name[]="unsigned int64"; return name; }
00063   
00064 protected:
00066   static const VTYP _typeMin;
00067   
00069   static const VTYP _typeMax;
00070   
00072   static const VTYP _typeDefault;
00073   
00075   static const char _typeInfoString[_ML_STD_SLEN];
00076   
00078 
00079   inline MLDataType _rangeAndPrecisionEquiv(MLint8   ) { return MLint8Type;    };
00080   inline MLDataType _rangeAndPrecisionEquiv(MLuint8  ) { return MLuint8Type;   };
00081   inline MLDataType _rangeAndPrecisionEquiv(MLint16  ) { return MLint16Type;   };
00082   inline MLDataType _rangeAndPrecisionEquiv(MLuint16 ) { return MLuint16Type;  };
00083   inline MLDataType _rangeAndPrecisionEquiv(MLint32  ) { return MLint32Type;   };
00084   inline MLDataType _rangeAndPrecisionEquiv(MLuint32 ) { return MLuint32Type;  };
00085   inline MLDataType _rangeAndPrecisionEquiv(MLfloat  ) { return MLfloatType;   };
00086   inline MLDataType _rangeAndPrecisionEquiv(MLdouble ) { return MLdoubleType;  };
00087   inline MLDataType _rangeAndPrecisionEquiv(MLint64  ) { return MLint64Type;   };
00088   inline MLDataType _rangeAndPrecisionEquiv(MLuint64 ) { return MLuint64Type;  };
00090 
00092   static inline       VTYP& value_cast(      MLTypeData* v) { return *(reinterpret_cast<      VTYP*>(v)); }
00093   static inline const VTYP& value_cast(const MLTypeData* v) { return *(reinterpret_cast<const VTYP*>(v)); }
00095 
00098   static inline VTYP castToType(MLdouble v)  { return static_cast<VTYP>(floor(v+0.5)); }
00099 
00101 
00102   inline void _getGoodCastTos(MLint8, MLuint &num, const char **&typeNames)
00103   {
00104     ML_TRACE_IN( "MLTStdTypeInfos::_getGoodCastTos( )" );
00105     ML_TRY
00106     {
00107       num = 5;
00108       static const char *v[] = 
00109       {
00110         MLTStdTypeInfos<MLint16  >::typeName(static_cast<MLint16  *>(NULL)),
00111         MLTStdTypeInfos<MLint32  >::typeName(static_cast<MLint32  *>(NULL)),
00112         MLTStdTypeInfos<MLfloat  >::typeName(static_cast<MLfloat  *>(NULL)),
00113         MLTStdTypeInfos<MLdouble >::typeName(static_cast<MLdouble *>(NULL)),
00114         MLTStdTypeInfos<MLint64  >::typeName(static_cast<MLint64  *>(NULL)) 
00115       };
00116       typeNames = v;
00117     }
00118     ML_CATCH_RETHROW;
00119   };
00120   inline void _getGoodCastTos(MLuint8, MLuint &num, const char **&typeNames)
00121   {
00122     ML_TRACE_IN( "MLTStdTypeInfos::_getGoodCastTos( )" );
00123     ML_TRY
00124     { 
00125       num = 8;
00126       static const char *v[] = 
00127       {
00128         MLTStdTypeInfos<MLint16  >::typeName(static_cast<MLint16  *>(NULL)),
00129         MLTStdTypeInfos<MLuint16 >::typeName(static_cast<MLuint16 *>(NULL)),
00130         MLTStdTypeInfos<MLint32  >::typeName(static_cast<MLint32  *>(NULL)),
00131         MLTStdTypeInfos<MLuint32 >::typeName(static_cast<MLuint32 *>(NULL)),
00132         MLTStdTypeInfos<MLfloat  >::typeName(static_cast<MLfloat  *>(NULL)),
00133         MLTStdTypeInfos<MLdouble >::typeName(static_cast<MLdouble *>(NULL)),
00134         MLTStdTypeInfos<MLint64  >::typeName(static_cast<MLint64  *>(NULL)),
00135         MLTStdTypeInfos<MLuint64 >::typeName(static_cast<MLuint64 *>(NULL)) 
00136       };
00137       typeNames = v;
00138     }
00139     ML_CATCH_RETHROW;
00140   };
00141   inline void _getGoodCastTos(MLint16, MLuint &num, const char **&typeNames)
00142   {
00143     ML_TRACE_IN( "MLTStdTypeInfos::_getGoodCastTos( )" );
00144     ML_TRY
00145     {      
00146       num = 4;
00147       static const char *v[] = 
00148       {
00149         MLTStdTypeInfos<MLint32  >::typeName(static_cast<MLint32  *>(NULL)),
00150         MLTStdTypeInfos<MLfloat  >::typeName(static_cast<MLfloat  *>(NULL)),
00151         MLTStdTypeInfos<MLdouble >::typeName(static_cast<MLdouble *>(NULL)),
00152         MLTStdTypeInfos<MLint64  >::typeName(static_cast<MLint64  *>(NULL)) 
00153       };
00154       typeNames = v;
00155     }
00156     ML_CATCH_RETHROW;
00157   };
00158   inline void _getGoodCastTos(MLuint16, MLuint &num, const char **&typeNames)
00159   {
00160     ML_TRACE_IN( "MLTStdTypeInfos::_getGoodCastTos( )" );
00161     ML_TRY
00162     {      
00163       num = 6;
00164       static const char *v[] = 
00165       {
00166         MLTStdTypeInfos<MLint32  >::typeName(static_cast<MLint32  *>(NULL)),
00167         MLTStdTypeInfos<MLuint32 >::typeName(static_cast<MLuint32 *>(NULL)),
00168         MLTStdTypeInfos<MLfloat  >::typeName(static_cast<MLfloat  *>(NULL)),
00169         MLTStdTypeInfos<MLdouble >::typeName(static_cast<MLdouble *>(NULL)),
00170         MLTStdTypeInfos<MLint64  >::typeName(static_cast<MLint64  *>(NULL)),
00171         MLTStdTypeInfos<MLuint64 >::typeName(static_cast<MLuint64 *>(NULL)) 
00172       };
00173       typeNames = v;
00174     }
00175     ML_CATCH_RETHROW;
00176   };
00177   inline void _getGoodCastTos(MLint32, MLuint &num, const char **&typeNames)
00178   {
00179     ML_TRACE_IN( "MLTStdTypeInfos::_getGoodCastTos( )" );
00180     ML_TRY
00181     {      
00182       num = 3;
00183       static const char *v[] = 
00184       {
00185         MLTStdTypeInfos<MLfloat  >::typeName(static_cast<MLfloat  *>(NULL)),
00186         MLTStdTypeInfos<MLdouble >::typeName(static_cast<MLdouble *>(NULL)),
00187         MLTStdTypeInfos<MLint64  >::typeName(static_cast<MLint64  *>(NULL)) 
00188       };
00189       typeNames = v;
00190     }
00191     ML_CATCH_RETHROW;
00192   };
00193   inline void _getGoodCastTos(MLuint32, MLuint &num, const char **&typeNames)
00194   {
00195     ML_TRACE_IN( "MLTStdTypeInfos::_getGoodCastTos( )" );
00196     ML_TRY
00197     {      
00198       num = 4;
00199       static const char *v[] = 
00200       {
00201         MLTStdTypeInfos<MLfloat  >::typeName(static_cast<MLfloat  *>(NULL)),
00202         MLTStdTypeInfos<MLdouble >::typeName(static_cast<MLdouble *>(NULL)),
00203         MLTStdTypeInfos<MLint64  >::typeName(static_cast<MLint64  *>(NULL)),
00204         MLTStdTypeInfos<MLuint64 >::typeName(static_cast<MLuint64 *>(NULL)) 
00205       };
00206       typeNames = v;
00207     }
00208     ML_CATCH_RETHROW;
00209   };
00210   inline void _getGoodCastTos(MLfloat, MLuint &num, const char **&typeNames)
00211   {
00212     ML_TRACE_IN( "MLTStdTypeInfos::_getGoodCastTos( )" );
00213     ML_TRY
00214     {      
00215       num = 1;
00216       static const char *v[] = 
00217       {
00218         MLTStdTypeInfos<MLdouble >::typeName(static_cast<MLdouble *>(NULL)),
00219       };
00220       typeNames = v;
00221     }
00222     ML_CATCH_RETHROW;
00223   };
00224   inline void _getGoodCastTos(MLdouble, MLuint &num, const char **&typeNames)
00225   {
00226     ML_TRACE_IN( "MLTStdTypeInfos::_getGoodCastTos( )" );
00227     ML_TRY
00228     {      
00229       num = 0;
00230       typeNames = NULL;
00231     }
00232     ML_CATCH_RETHROW;
00233   };
00234   inline void _getGoodCastTos(MLint64, MLuint &num, const char **&typeNames)
00235   {
00236     ML_TRACE_IN( "MLTStdTypeInfos::_getGoodCastTos( )" );
00237     ML_TRY
00238     {      
00239       num = 2;
00240       static const char *v[] = 
00241       {
00242         MLTStdTypeInfos<MLfloat  >::typeName(static_cast<MLfloat  *>(NULL)),
00243         MLTStdTypeInfos<MLdouble >::typeName(static_cast<MLdouble *>(NULL)),
00244       };
00245       typeNames = v;
00246     }
00247     ML_CATCH_RETHROW;
00248   };
00249   inline void _getGoodCastTos(MLuint64, MLuint &num, const char **&typeNames)
00250   {
00251     ML_TRACE_IN( "MLTStdTypeInfos::_getGoodCastTos( )" );
00252     ML_TRY
00253     {      
00254       num = 2;
00255       static const char *v[] = 
00256       {
00257         MLTStdTypeInfos<MLfloat  >::typeName(static_cast<MLfloat  *>(NULL)),
00258         MLTStdTypeInfos<MLdouble >::typeName(static_cast<MLdouble *>(NULL)),
00259       };
00260       typeNames = v;
00261     }
00262     ML_CATCH_RETHROW;
00263   };
00265   
00267   static MLTypeInfos *_myInfos;
00268   
00271   static MLint32      _numInstances;
00272   
00273 public:
00274   
00278   MLTStdTypeInfos()
00279   {
00280     ML_TRACE_IN( "MLTStdTypeInfos::MLTStdTypeInfos( )" );
00281     ML_TRY
00282     {
00283       if (_numInstances > 0)
00284       {
00285         ML_PRINT_FATAL_ERROR("MLTStdTypeInfos", ML_PROGRAMMING_ERROR, "Too many instances of MLTStdTypeInfos created.");
00286         ML_CHECK_THROW(0);
00287       }
00288       _numInstances++;
00289       
00290       // Save pointer to the one instance of this class.
00291       _myInfos     = this;
00292       
00294       ML_TYPE_ASSIGN_FUNCTION_POINTERS();
00295       
00296       // Determine the type to which this type can be casted without information loss.
00297       MLuint numLocalGoodCastTos=0;
00298       const char **goodLocalCastTos=NULL;
00299       _getGoodCastTos(static_cast<VTYP>(0), numLocalGoodCastTos, goodLocalCastTos);
00300       
00360       VTYP buf=0;
00361       void *addr[1];
00362       addr[0] = &buf;
00363       MLTypeInfosInit(this,                        
00364                       sizeof(VTYP),                
00365                       typeName(static_cast<VTYP*>(NULL)),
00366                       _typeMin,       
00367                       _typeMax,        
00368                       reinterpret_cast<const MLTypeData*>(&_typeMin),    
00369                       reinterpret_cast<const MLTypeData*>(&_typeMax),    
00370                       reinterpret_cast<const MLTypeData*>(&_typeDefault),
00371                       _typeInfoString,             
00372                       true,
00373                       MLScalarTypeGroup,
00374                       _rangeAndPrecisionEquiv(static_cast<VTYP>(0)),
00375                       addr,
00376                       numLocalGoodCastTos,
00377                       goodLocalCastTos
00378                       );
00379     }
00380     ML_CATCH_RETHROW;
00381   }
00382   
00383   
00384   //-------------------------------------------------------------------------------
00385   // Methods to be overloaded:
00386   //-------------------------------------------------------------------------------
00387   
00389 
00390   
00392   static char       *MLTYPE_getStringValue        (const MLTypeData *p)                                       { return MLTypeComponentsToString(_myInfos, p); }
00394   static void        MLTYPE_setStringValue        (const char *s, MLTypeData *r)                              { MLTypeComponentsFromString(_myInfos, s, reinterpret_cast<const MLTypeData*>(&_typeDefault), r); }
00395   
00397   static void        MLTYPE_setToMinimum          (MLTypeData *p)                                             { value_cast(p) = _typeMin; }
00399   static void        MLTYPE_setToMaximum          (MLTypeData *p)                                             { value_cast(p) = _typeMax; }
00401   static void        MLTYPE_setToDefault          (MLTypeData *p)                                             { value_cast(p) = _typeDefault; }
00403   static MLdouble    MLTYPE_getComponent          (const MLTypeData *p, size_t /*n*/)                         { return static_cast<MLdouble>(value_cast(p)); }
00405   static void        MLTYPE_setComponent          (MLTypeData *p, size_t /*n*/, MLdouble v)                   { value_cast(p) = static_cast<VTYP>(v); }
00407   static void        MLTYPE_copy                  (const MLTypeData *p, MLTypeData *q)                        { value_cast(q) = value_cast(p); }
00409   static void        MLTYPE_arrayCopy             (const MLTypeData *p, MLTypeData *q, size_t n)              { memcpy(q, p, sizeof(VTYP)*n); }
00411   static void        MLTYPE_arrayCopyWithStrides  (const MLTypeData *p, MLssize_t ps, MLTypeData *q, MLssize_t qs, size_t n) { for (size_t i=0;i<n;i++) { value_cast(q) = value_cast(p); q += sizeof(VTYP)*qs; p += sizeof(VTYP)*ps; } }
00413   static void        MLTYPE_arrayFill             (const MLTypeData *p, MLTypeData *q, size_t n)              { for (size_t i=0;i<n;i++) { value_cast(q) = value_cast(p); q += sizeof(VTYP); } }
00414   
00416   static bool        MLTYPE_castToBool            (const MLTypeData *p)                                       { return MLValuesDifferWOM(value_cast(p), static_cast<VTYP>(0)); }
00418   static MLint       MLTYPE_castToInt             (const MLTypeData *p)                                       { return static_cast<MLint>(value_cast(p)); }
00420   static MLdouble    MLTYPE_castToDouble          (const MLTypeData *p)                                       { return static_cast<MLdouble>(value_cast(p)); }
00422   static void        MLTYPE_castToOtherType(const MLTypeData *myData, const MLTypeInfos *otherInfos, MLTypeData *otherData) { MLTypeCastToOtherType(_myInfos, myData,  otherInfos, otherData); }
00423   
00425   static void        MLTYPE_castFromInt           (MLint p, MLTypeData *q)                                  { value_cast(q) = static_cast<VTYP>(p); }
00427   static void        MLTYPE_castFromDouble        (MLdouble p, MLTypeData *q)                                 { value_cast(q) = static_cast<VTYP>(p); }
00429   static void        MLTYPE_castFromOtherType     (const MLTypeInfos *otherInfos, const MLTypeData *otherData, 
00430                                                    MLTypeData *myData)                                        { MLTypeCastToOtherType(otherInfos,otherData, _myInfos, myData);   }
00431     
00433   static bool        MLTYPE_isEqualToType         (const MLTypeData *p, const MLTypeData *q)                  { return MLValuesAreEqualWOM(value_cast(p), value_cast(q)); }
00435   static bool        MLTYPE_isEqualToTypeWithEpsilon(const MLTypeData *p, const MLTypeData *q, MLdouble eps)  { return MLAbs(value_cast(p)-value_cast(q)) < eps; }
00436   
00438   static void        MLTYPE_negate                (const MLTypeData *p, MLTypeData *q)                        { value_cast(q) = -value_cast(p); }
00439   
00441   static void        MLTYPE_normalize             (const MLTypeData * /*p*/, MLTypeData *q)                   { value_cast(q) = 1; }
00442   
00446   static void        MLTYPE_arrayRescale          (const MLTypeData* p, MLdouble q, const MLTypeData* r, MLTypeData* t, size_t s) {
00447     for (size_t i=0;i<s;i++) {
00448       value_cast(t) = castToType(value_cast(p) * q + value_cast(r));
00449       t += sizeof(VTYP);
00450       p += sizeof(VTYP);
00451     }
00452   }
00453 
00457   static bool        MLTYPE_arrayEqualsValue     (const MLTypeData* p, const MLTypeData* q, size_t s) {
00458     for (size_t i=0;i<s;i++) {
00459       if (value_cast(p) != value_cast(q)) { return false; }
00460       q += sizeof(VTYP);
00461     }
00462     return true;
00463   }
00464 
00468   static void        MLTYPE_arrayGetMinMax       (const MLTypeData* p, size_t s, MLdouble& min, MLdouble& max) {
00469     MLdouble tmpMin, tmpMax;
00470     tmpMin = tmpMax = value_cast(p);
00471     p += sizeof(VTYP);
00472     for (size_t i=1;i<s;i++) {
00473       const VTYP v = value_cast(p);
00474       if (v < tmpMin) { tmpMin = v; }
00475       if (v > tmpMax) { tmpMax = v; }
00476       p += sizeof(VTYP);
00477     }
00478     min = tmpMin;
00479     max = tmpMax;
00480   }
00481 
00482 
00486   static void        MLTYPE_interpolate           (const MLTypeData* p, const MLTypeData* q, MLdouble r, MLTypeData* t) {
00487     value_cast(t) = castToType(value_cast(p) * (1.0-r) + value_cast(q) * r);
00488   }
00489 
00491   static void        MLTYPE_multWithInt           (const MLTypeData *p, MLint q,             MLTypeData *r)   { value_cast(r) = static_cast<VTYP>(value_cast(p) * q);   }
00493   static void        MLTYPE_multWithDouble        (const MLTypeData *p, MLdouble q,          MLTypeData *r)   { value_cast(r) = static_cast<VTYP>(value_cast(p) * q);   }
00495   static void        MLTYPE_multWithType          (const MLTypeData *p, const MLTypeData *q, MLTypeData *r)   { value_cast(r) = value_cast(p)*value_cast(q); }
00497   static void        MLTYPE_multWithOtherType     (const MLTypeInfos *otherInfos, const MLTypeData *otherData, 
00498                                                    const MLTypeData *myData, MLTypeData *r)                   { MLTypeMultWithOtherType(_myInfos, myData, otherInfos, otherData, r); }
00499   
00501   static void        MLTYPE_plusInt          (const MLTypeData *p, MLint q,             MLTypeData *r)   { value_cast(r) = value_cast(p) + q;                     }
00503   static void        MLTYPE_plusDouble       (const MLTypeData *p, MLdouble q,          MLTypeData *r)   { value_cast(r) = static_cast<VTYP>(value_cast(p) + q);  }
00505   static void        MLTYPE_plusType         (const MLTypeData *p, const MLTypeData *q, MLTypeData *r)   { value_cast(r) = value_cast(p) + value_cast(q);         }
00506   
00508 };
00509 
00510 template<> inline MLfloat   MLTStdTypeInfos<MLfloat  >::castToType(MLdouble v) { return static_cast<MLfloat  >(v); }
00511 template<> inline MLdouble  MLTStdTypeInfos<MLdouble >::castToType(MLdouble v) { return v;                         }
00512 
00513 
00514 // For unsigned types implement specialized negations to avoid warning due to negations of unsigned types. We just copy instead of negating.
00515 template<> inline void MLTStdTypeInfos<MLuint8  >::MLTYPE_negate      (const MLTypeData *p, MLTypeData *q)                     { value_cast(q) = value_cast(p);   }
00516 template<> inline void MLTStdTypeInfos<MLuint16 >::MLTYPE_negate      (const MLTypeData *p, MLTypeData *q)                     { value_cast(q) = value_cast(p);   }
00517 template<> inline void MLTStdTypeInfos<MLuint32 >::MLTYPE_negate      (const MLTypeData *p, MLTypeData *q)                     { value_cast(q) = value_cast(p);   }
00518 template<> inline void MLTStdTypeInfos<MLuint64 >::MLTYPE_negate      (const MLTypeData *p, MLTypeData *q)                     { value_cast(q) = value_cast(p);   }
00519 
00520 
00521 // Member initializations for unspecialized class members.
00522 template <typename VTYP> const VTYP   MLTStdTypeInfos<VTYP>::_typeDefault                  = VTYP(0);
00523 template <typename VTYP> MLTypeInfos* MLTStdTypeInfos<VTYP>::_myInfos                      = NULL;
00524 template <typename VTYP> MLint32      MLTStdTypeInfos<VTYP>::_numInstances                 = 0;
00525 
00526 ML_END_NAMESPACE
00527 
00528 #ifdef _MSC_VER
00529 #pragma warning(pop)
00530 #endif
00531 
00532 
00533 #endif //of __mlStdTypeInfos_H
00534 
00535 
00536