00001 #ifndef realroot_ARITHM_TEXP_OPERATORS_H
00002 #define realroot_ARITHM_TEXP_OPERATORS_H
00003
00004 #include <realroot/texp_double.hpp>
00005 #include <realroot/texp_expression.hpp>
00006
00007 namespace mmx {
00008
00009 #define define_binary_operator_structure(opname,function,call) \
00010 \
00011 struct opname \
00012 { \
00013 inline static const char * name() { return #call; }; \
00014 template < class A, class B, class C > inline \
00015 void operator()( A & a, const B & b, const C & c) const \
00016 { \
00017 call (a, b, c); \
00018 }; \
00019 template < class A, class B > inline \
00020 void operator()( A & a, const B & b ) const \
00021 { \
00022 call (a, b); \
00023 }; \
00024 }; \
00025
00026 #define define_binary_operator(opname,function,call)\
00027 define_binary_operator_structure(opname,function,call)\
00028 template<class X, class Y> inline \
00029 texp::template_expression< \
00030 texp::binary_operator<opname, \
00031 texp::template_expression<X>, \
00032 texp::template_expression<Y> > > \
00033 function( const texp::template_expression<X>& x, \
00034 const texp::template_expression<Y>& y ) \
00035 { \
00036 return texp::template_expression< texp::binary_operator< opname, \
00037 texp::template_expression<X>, \
00038 texp::template_expression<Y> > > ( x, y ); \
00039 }; \
00040 \
00041 template<class X, class Y> inline \
00042 texp::template_expression< \
00043 texp::binary_operator<opname, \
00044 texp::template_expression<X>, \
00045 texp::template_expression<Y> > > \
00046 function( const texp::template_expression<X>& x, const Y& y ) \
00047 { \
00048 return texp::template_expression< texp::binary_operator< opname, \
00049 texp::template_expression<X>, \
00050 texp::template_expression<Y> > > \
00051 ( x, texp::template_expression<Y>(y)); \
00052 }; \
00053 \
00054 template<class X, class Y> inline \
00055 texp::template_expression< \
00056 texp::binary_operator<opname, \
00057 texp::template_expression<X>, \
00058 texp::template_expression<Y> > > \
00059 function( const X& x, const texp::template_expression<Y>& y ) \
00060 { \
00061 return \
00062 texp::template_expression< texp::binary_operator<opname \
00063 , texp::template_expression<X> \
00064 , texp::template_expression<Y> > > \
00065 (texp::template_expression<X>(x),y); \
00066 }; \
00067 \
00068 template<class X,class Y> \
00069 X & call( X & r, const texp::template_expression<Y> & exp ) \
00070 { \
00071 typename template_expression<Y>::E tmp; \
00072 exp.eval(tmp); \
00073 call(r,tmp); \
00074 return r; \
00075 } \
00076
00077 #define define_unary_operator(opname,function,call)\
00078 \
00079 struct opname \
00080 { \
00081 inline static const char * name() \
00082 { \
00083 return #call; \
00084 }; \
00085 \
00086 template < class A, class B > inline \
00087 void operator()(A & a, const B & b) const \
00088 { \
00089 call (a, b); \
00090 }; \
00091 template < class A> inline \
00092 void operator()(A & a) const \
00093 { \
00094 call (a); \
00095 }; \
00096 }; \
00097 \
00098 template<class X> inline \
00099 texp::template_expression< \
00100 unary_operator< opname, \
00101 texp::template_expression<X> > > \
00102 function( const texp::template_expression<X>& x ) \
00103 { \
00104 return \
00105 texp::template_expression< \
00106 unary_operator<opname, texp::template_expression<X> > >( x ); \
00107 }; \
00108 \
00109 template<class X> inline \
00110 texp::template_expression< \
00111 unary_operator< opname, \
00112 texp::template_expression<X> > > \
00113 function( const X& x ) \
00114 { \
00115 return \
00116 texp::template_expression< \
00117 unary_operator<opname, texp::template_expression<X> > > \
00118 ( texp::template_expression<X>(x) ); \
00119 }; \
00120
00121 #define declare_binary_operator(tp_arg_list,parm0,parm1,opname,function)\
00122 tp_arg_list inline \
00123 texp::template_expression< texp::binary_operator< opname,\
00124 texp::template_expression< parm0 >, \
00125 texp::template_expression< parm1 > > > \
00126 function( const parm0 & x, const parm1 & y )\
00127 { return \
00128 texp::template_expression< \
00129 texp::binary_operator< \
00130 opname, texp::template_expression< parm0 >, texp::template_expression< parm1 > > >\
00131 (texp::template_expression< parm0 >(x),texp::template_expression< parm1 >(y));\
00132 };\
00133 tp_arg_list inline \
00134 texp::template_expression< texp::binary_operator< opname , \
00135 texp::template_expression< parm0 >,\
00136 texp::template_expression< parm1 > > >\
00137 function( const texp::template_expression<parm0> & x, const parm1 & y )\
00138 { return texp::template_expression< texp::binary_operator< opname, texp::template_expression< parm0 >, texp::template_expression< parm1 > > >\
00139 (x,texp::template_expression<parm1>(y)); };\
00140 tp_arg_list inline \
00141 texp::template_expression< texp::binary_operator< opname , \
00142 texp::template_expression< parm0 >, \
00143 texp::template_expression< parm1 > > >\
00144 function( const parm0 & x, const texp::template_expression<parm1> & y )\
00145 { return texp::template_expression< texp::binary_operator< opname, texp::template_expression< parm0 >, texp::template_expression< parm1 > > >\
00146 (texp::template_expression< parm0 >(x),y); }
00147
00148 #define declare_unary_operator(tp_arg_list,parm,opname,function)\
00149 tp_arg_list inline \
00150 texp::template_expression< texp::unary_operator< opname, \
00151 texp::template_expression<parm> > >\
00152 function( const parm& x ) \
00153 { \
00154 return texp::template_expression<\
00155 texp::unary_operator< opname, \
00156 texp::template_expression<parm> > >( texp::template_expression<parm>(x) ); \
00157 };\
00158
00159
00160 }
00161
00162 #endif