Perhaps you could use std::plus<T> , std::minus<T> , std::multiplies<T> and std::divides<T> . However, they will only work if both operands are of the same type or, possibly, if the left can be converted to the type of the first.
I see no way to achieve what you are trying to do, except using a preprocessor. Any good reason for not wanting macros?
If you want to make sure that the return type is large enough to contain the result, you can do something like this:
#include <functional> #include <boost/mpl/if_.hpp> // Metafunction returning the largest type between T and U // Might already exist in Boost but I can't find it right now...maybe // boost::math::tools::promote_args template <typename T, typename U> struct largest : boost::mpl::if_< boost::mpl::bool_<(sizeof(T) > sizeof(U))>, T, U > {}; template <typename T, typename U, template <typename S> class Op> struct Foo { typedef typename largest<T, U>::type largeType; largeType bar(const T & t, const U & u) { return Op<largeType>()(t, u); // Applies operator+ } }; int main() { Foo<int, double, std::plus> f; double d = f.bar(12, 13.0); // takes int and double, returns double }
Here I used Boost MPL to write the largest metafile, but you could write your own if metafile if you cannot use Boost (a template template parameterized by two types and a bool specialized for true and false).
To determine the type of return expression, you can also look at boost :: result_of , which, if I understand correctly, is equivalent to the upcoming decltype operator in C ++ 0x.
source share