00001
00002
00003
00004
00005
00006
00007
00008
00009
00010
00011
00012
00013
00014
00015
00016
00017
00018
00019
00020
00021
00022
00023
00024
00025
00027 #ifndef SHSTORAGETYPEIMPL_HPP
00028 #define SHSTORAGETYPEIMPL_HPP
00029
00030 #include <climits>
00031 #include <cmath>
00032 #include <algorithm>
00033 #include "ShStorageType.hpp"
00034
00035 namespace SH {
00036
00037 inline bool shIsFloat(ShValueType value_type)
00038 {
00039 return !shIsInvalidValueType(value_type) &&
00040 (value_type & SH_VALUETYPE_TYPE_MASK) == SH_VALUETYPE_TYPE_FLOAT;
00041 }
00042
00043 inline bool shIsInteger(ShValueType value_type)
00044 {
00045 return !shIsInvalidValueType(value_type) &&
00046 (value_type & SH_VALUETYPE_TYPE_MASK) == SH_VALUETYPE_TYPE_INT;
00047 }
00048
00049 inline bool shIsFraction(ShValueType value_type)
00050 {
00051 return !shIsInvalidValueType(value_type) &&
00052 (value_type & SH_VALUETYPE_TYPE_MASK) == SH_VALUETYPE_TYPE_FRAC;
00053 }
00054
00055 inline bool shIsSigned(ShValueType value_type)
00056 {
00057 return !shIsInvalidValueType(value_type) &&
00058 (value_type & SH_VALUETYPE_SIGNED_MASK) == SH_VALUETYPE_SIGNED;
00059 }
00060
00061 inline bool shIsRegularValueType(ShValueType value_type)
00062 {
00063 return !shIsInvalidValueType(value_type) &&
00064 (value_type & SH_VALUETYPE_SPECIAL_MASK) == SH_VALUETYPE_SPECIAL_NONE;
00065 }
00066
00067 inline bool shIsInterval(ShValueType value_type)
00068 {
00069 return !shIsInvalidValueType(value_type) &&
00070 (value_type & SH_VALUETYPE_SPECIAL_MASK) == SH_VALUETYPE_SPECIAL_I;
00071 }
00072
00073 inline bool shIsInvalidValueType(ShValueType value_type)
00074 {
00075 return value_type == SH_VALUETYPE_END;
00076 }
00077
00078 inline
00079 ShValueType shIntervalValueType(ShValueType value_type)
00080 {
00081 return shIsInterval(value_type) ? value_type :
00082 shIsFloat(value_type) ? (value_type | SH_VALUETYPE_SPECIAL_I) :
00083 SH_VALUETYPE_END;
00084 }
00085
00086 inline
00087 ShValueType shRegularValueType(ShValueType value_type)
00088 {
00089 return shIsInvalidValueType(value_type) ? value_type :
00090 (value_type & ~SH_VALUETYPE_SPECIAL_MASK);
00091 }
00092
00093
00094
00095 #define SH_MATCH(V) ((V == V1) || (V == V2))
00096 template<typename T1, typename T2>
00097 struct ShCommonType {
00098 static const ShValueType V1 = ShStorageTypeInfo<T1>::value_type;
00099 static const ShValueType V2 = ShStorageTypeInfo<T2>::value_type;
00100 static const bool isFraction1 = ShIsFraction<T1>::matches;
00101 static const bool isFraction2 = ShIsFraction<T2>::matches;
00102 static const ShValueType value_type =
00103 ((SH_MATCH(SH_I_DOUBLE) || (SH_MATCH(SH_I_FLOAT) && SH_MATCH(SH_DOUBLE))) ?
00104 SH_I_DOUBLE :
00105 (SH_MATCH(SH_I_FLOAT) ?
00106 SH_I_FLOAT :
00107 (SH_MATCH(SH_DOUBLE) ?
00108 SH_DOUBLE :
00109 (SH_MATCH(SH_FLOAT) || isFraction1 || isFraction2) ?
00110 SH_FLOAT :
00111 ((V1 == SH_HALF && V2 == SH_HALF) ?
00112 SH_HALF :
00113 SH_INT))));
00114 typedef typename ShValueTypeInfo<value_type>::storage_type type;
00115 };
00116 #undef SH_MATCH
00117
00118
00119 }
00120
00121 #endif