[ VIGRA Homepage | Function Index | Class Index | Namespaces | File List | Main Page ]
00001 /************************************************************************/ 00002 /* */ 00003 /* Copyright 1998-2005 by Ullrich Koethe */ 00004 /* */ 00005 /* This file is part of the VIGRA computer vision library. */ 00006 /* The VIGRA Website is */ 00007 /* http://hci.iwr.uni-heidelberg.de/vigra/ */ 00008 /* Please direct questions, bug reports, and contributions to */ 00009 /* ullrich.koethe@iwr.uni-heidelberg.de or */ 00010 /* vigra@informatik.uni-hamburg.de */ 00011 /* */ 00012 /* Permission is hereby granted, free of charge, to any person */ 00013 /* obtaining a copy of this software and associated documentation */ 00014 /* files (the "Software"), to deal in the Software without */ 00015 /* restriction, including without limitation the rights to use, */ 00016 /* copy, modify, merge, publish, distribute, sublicense, and/or */ 00017 /* sell copies of the Software, and to permit persons to whom the */ 00018 /* Software is furnished to do so, subject to the following */ 00019 /* conditions: */ 00020 /* */ 00021 /* The above copyright notice and this permission notice shall be */ 00022 /* included in all copies or substantial portions of the */ 00023 /* Software. */ 00024 /* */ 00025 /* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND */ 00026 /* EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES */ 00027 /* OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND */ 00028 /* NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT */ 00029 /* HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, */ 00030 /* WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING */ 00031 /* FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR */ 00032 /* OTHER DEALINGS IN THE SOFTWARE. */ 00033 /* */ 00034 /************************************************************************/ 00035 00036 00037 #ifndef VIGRA_FUNCTORTRAITS_HXX 00038 #define VIGRA_FUNCTORTRAITS_HXX 00039 00040 #include <functional> 00041 #include "metaprogramming.hxx" 00042 00043 namespace vigra { 00044 00045 struct InitializerTag {}; 00046 struct UnaryFunctorTag {}; 00047 struct BinaryFunctorTag {}; 00048 struct TernaryFunctorTag {}; 00049 struct UnaryAnalyserTag {}; 00050 struct BinaryAnalyserTag {}; 00051 struct TernaryAnalyserTag {}; 00052 00053 struct UnaryReduceFunctorTag 00054 : public InitializerTag, public UnaryAnalyserTag 00055 {}; 00056 00057 struct BinaryReduceFunctorTag 00058 : public InitializerTag, public BinaryAnalyserTag 00059 {}; 00060 00061 typedef UnaryFunctorTag UnaryExpandFunctorTag; 00062 typedef BinaryFunctorTag BinaryExpandFunctorTag; 00063 00064 template <class T> 00065 class FunctorTraitsBase 00066 { 00067 public: 00068 typedef T type; 00069 00070 typedef typename IsDerivedFrom<T, InitializerTag>::result isInitializer; 00071 00072 typedef typename IsDerivedFrom<T, UnaryFunctorTag>::result isUnaryFunctor; 00073 typedef typename IsDerivedFrom<T, BinaryFunctorTag>::result isBinaryFunctor; 00074 typedef typename IsDerivedFrom<T, TernaryFunctorTag>::result isTernaryFunctor; 00075 00076 typedef typename IsDerivedFrom<T, UnaryAnalyserTag>::result isUnaryAnalyser; 00077 typedef typename IsDerivedFrom<T, BinaryAnalyserTag>::result isBinaryAnalyser; 00078 typedef typename IsDerivedFrom<T, TernaryAnalyserTag>::result isTernaryAnalyser; 00079 }; 00080 00081 00082 00083 /** \addtogroup Functors 00084 */ 00085 //@{ 00086 /** \brief Export associated information for a functor. 00087 00088 The FunctorTraits class contains the following fields: 00089 00090 \code 00091 template <class T> 00092 struct FunctorTraits 00093 { 00094 typedef T type; 00095 00096 typedef ... isInitializer; 00097 00098 typedef ... isUnaryFunctor; 00099 typedef ... isBinaryFunctor; 00100 typedef ... isTernaryFunctor; 00101 00102 typedef ... isUnaryAnalyser; 00103 typedef ... isBinaryAnalyser; 00104 typedef ... isTernaryAnalyser; 00105 }; 00106 \endcode 00107 00108 where the dots are either <tt>VigraTrueType</tt> or <tt>VigraFalseType</tt> 00109 depending on whether the functor supports the respective functionality or not. 00110 Note that these traits are automatically defined correctly when your functor is derived 00111 from the appropriate functor tag classes: 00112 00113 \code 00114 struct InitializerTag {}; 00115 struct UnaryFunctorTag {}; 00116 struct BinaryFunctorTag {}; 00117 struct TernaryFunctorTag {}; 00118 struct UnaryAnalyserTag {}; 00119 struct BinaryAnalyserTag {}; 00120 struct TernaryAnalyserTag {}; 00121 struct UnaryReduceFunctorTag : public InitializerTag, public UnaryAnalyserTag {}; 00122 struct BinaryReduceFunctorTag : public InitializerTag, public BinaryAnalyserTag {}; 00123 \endcode 00124 00125 If a functor <tt>f</tt> is a model of these categories, it supports the following 00126 calls (<tt>v</tt> is a variable such that the result type of the functor 00127 calls can be converted into <tt>v</tt>'s type, and <tt>a1, a2, a3</tt> are 00128 variables convertible into the functor's argument types): 00129 00130 <DL> 00131 <DT><b>Initializer</b> 00132 <DD> <tt>v = f()</tt> (used with initImageWithFunctor()) 00133 <DT><b>UnaryFunctor</b> 00134 <DD> <tt>v = f(a1)</tt> (used with transformImage()) 00135 <DT><b>BinaryFunctor</b> 00136 <DD> <tt>v = f(a1, a2)</tt> (used with combineTwoImages()) 00137 <DT><b>TernaryFunctor</b> 00138 <DD> <tt>v = f(a1, a2, a3)</tt> (used with combineThreeImages()) 00139 <DT><b>UnaryAnalyser</b> 00140 <DD> <tt>f(a1)</tt> (return type <tt>void</tt>, used with inspectImage()) 00141 <DT><b>BinaryAnalyser</b> 00142 <DD> <tt>f(a1, a2)</tt> (return type <tt>void</tt>, used with inspectTwoImages()) 00143 <DT><b>TernaryAnalyser</b> 00144 <DD> <tt>f(a1, a2, a3)</tt> (return type <tt>void</tt>) 00145 </DL> 00146 00147 It should be noted that the functor's argument and result types are not contained 00148 in the traits class: Since the function calls are often member template functions in 00149 VIGRA, many functors do not have fixed argument types. Neither are the result 00150 types fixed in this case because they are computed (via a template meta-program) 00151 from the argument types. 00152 00153 <b>\#include</b> <<a href="functortraits_8hxx-source.html">vigra/functortraits.hxx</a>> 00154 Namespace: vigra 00155 */ 00156 template <class T> 00157 class FunctorTraits 00158 : public FunctorTraitsBase<T> 00159 {}; 00160 00161 #define VIGRA_DEFINE_STL_FUNCTOR(name, unary, binary) \ 00162 template <class T> \ 00163 class FunctorTraits<name<T> > \ 00164 { \ 00165 public: \ 00166 typedef T type; \ 00167 \ 00168 typedef VigraFalseType isInitializer; \ 00169 \ 00170 typedef unary isUnaryFunctor; \ 00171 typedef binary isBinaryFunctor; \ 00172 typedef VigraFalseType isTernaryFunctor; \ 00173 \ 00174 typedef VigraFalseType isUnaryAnalyser; \ 00175 typedef VigraFalseType isBinaryAnalyser; \ 00176 typedef VigraFalseType isTernaryAnalyser; \ 00177 }; 00178 00179 // ???TODO: these should also be specialized for the ptr_fun and mem_fun_ptr wrappers 00180 VIGRA_DEFINE_STL_FUNCTOR(std::plus, VigraFalseType, VigraTrueType) 00181 VIGRA_DEFINE_STL_FUNCTOR(std::minus, VigraFalseType, VigraTrueType) 00182 VIGRA_DEFINE_STL_FUNCTOR(std::multiplies, VigraFalseType, VigraTrueType) 00183 VIGRA_DEFINE_STL_FUNCTOR(std::divides, VigraFalseType, VigraTrueType) 00184 VIGRA_DEFINE_STL_FUNCTOR(std::modulus, VigraFalseType, VigraTrueType) 00185 VIGRA_DEFINE_STL_FUNCTOR(std::equal_to, VigraFalseType, VigraTrueType) 00186 VIGRA_DEFINE_STL_FUNCTOR(std::not_equal_to, VigraFalseType, VigraTrueType) 00187 VIGRA_DEFINE_STL_FUNCTOR(std::greater, VigraFalseType, VigraTrueType) 00188 VIGRA_DEFINE_STL_FUNCTOR(std::less, VigraFalseType, VigraTrueType) 00189 VIGRA_DEFINE_STL_FUNCTOR(std::greater_equal, VigraFalseType, VigraTrueType) 00190 VIGRA_DEFINE_STL_FUNCTOR(std::less_equal, VigraFalseType, VigraTrueType) 00191 VIGRA_DEFINE_STL_FUNCTOR(std::logical_and, VigraFalseType, VigraTrueType) 00192 VIGRA_DEFINE_STL_FUNCTOR(std::logical_or, VigraFalseType, VigraTrueType) 00193 VIGRA_DEFINE_STL_FUNCTOR(std::binary_negate, VigraFalseType, VigraTrueType) 00194 00195 VIGRA_DEFINE_STL_FUNCTOR(std::negate, VigraTrueType, VigraFalseType) 00196 VIGRA_DEFINE_STL_FUNCTOR(std::logical_not, VigraTrueType, VigraFalseType) 00197 VIGRA_DEFINE_STL_FUNCTOR(std::unary_negate, VigraTrueType, VigraFalseType) 00198 VIGRA_DEFINE_STL_FUNCTOR(std::binder1st, VigraTrueType, VigraFalseType) 00199 VIGRA_DEFINE_STL_FUNCTOR(std::binder2nd, VigraTrueType, VigraFalseType) 00200 #undef VIGRA_DEFINE_STL_FUNCTOR 00201 00202 template <class R> 00203 class FunctorTraits<R (*)()> 00204 { 00205 public: 00206 typedef R (*type)(); 00207 00208 typedef VigraTrueType isInitializer; 00209 typedef VigraFalseType isUnaryFunctor; 00210 typedef VigraFalseType isBinaryFunctor; 00211 typedef VigraFalseType isTernaryFunctor; 00212 typedef VigraFalseType isUnaryAnalyser; 00213 typedef VigraFalseType isBinaryAnalyser; 00214 typedef VigraFalseType isTernaryAnalyser; 00215 }; 00216 00217 template <class R, class T> 00218 class FunctorTraits<R (*)(T)> 00219 { 00220 public: 00221 typedef R (*type)(T); 00222 00223 typedef VigraFalseType isInitializer; 00224 typedef VigraTrueType isUnaryFunctor; 00225 typedef VigraFalseType isBinaryFunctor; 00226 typedef VigraFalseType isTernaryFunctor; 00227 typedef VigraFalseType isUnaryAnalyser; 00228 typedef VigraFalseType isBinaryAnalyser; 00229 typedef VigraFalseType isTernaryAnalyser; 00230 }; 00231 00232 template <class R, class T1, class T2> 00233 class FunctorTraits<R (*)(T1, T2)> 00234 { 00235 public: 00236 typedef R (*type)(T1, T2); 00237 00238 typedef VigraFalseType isInitializer; 00239 typedef VigraFalseType isUnaryFunctor; 00240 typedef VigraTrueType isBinaryFunctor; 00241 typedef VigraFalseType isTernaryFunctor; 00242 typedef VigraFalseType isUnaryAnalyser; 00243 typedef VigraFalseType isBinaryAnalyser; 00244 typedef VigraFalseType isTernaryAnalyser; 00245 }; 00246 00247 template <class R, class T1, class T2, class T3> 00248 class FunctorTraits<R (*)(T1, T2, T3)> 00249 { 00250 public: 00251 typedef R (*type)(T1, T2, T3); 00252 00253 typedef VigraFalseType isInitializer; 00254 typedef VigraFalseType isUnaryFunctor; 00255 typedef VigraFalseType isBinaryFunctor; 00256 typedef VigraTrueType isTernaryFunctor; 00257 typedef VigraFalseType isUnaryAnalyser; 00258 typedef VigraFalseType isBinaryAnalyser; 00259 typedef VigraFalseType isTernaryAnalyser; 00260 }; 00261 00262 //@} 00263 00264 } // namespace vigra 00265 00266 #endif // VIGRA_FUNCTORTRAITS_HXX
© Ullrich Köthe (ullrich.koethe@iwr.uni-heidelberg.de) |
html generated using doxygen and Python
|