开发者

Using template specialization in C++

开发者 https://www.devze.com 2023-02-03 02:34 出处:网络
How can I write a 开发者_如何转开发function using template specialization that has 2 different input types and an output type:

How can I write a 开发者_如何转开发function using template specialization that has 2 different input types and an output type:

template <class input1, class input2, class output>

and return the sum of the 2 numbers (integers/doubles). However, if I get 2 integers I want to return an integer type but for any other combinations of integer and double I'll always return double.

I am trying to do that without using directly the '+' operator but having the next functions instead:

double add_double_double(double a, double b) {return (a+b);}
double add_int_double(int a, double b) {return ((double)(a)+b);}
int   add_int_int(int a, int b) {return (a+b);}


If you can use C++0x, you could do this:

template <typename T, typename U>
auto add(T lhs, U rhs) -> decltype(lhs+rhs)
{
    return lhs+rhs;
}


Don’t use template specialization. Use overloading instead. Specializing functions is complicated and rarely needed:

template <typename T1, typename T2>
double sum(T1 a, T2 b) { return a + b; }

int sum(int a, int b) { return a + b; }

The second version will be called if and only if both arguments are int; otherwise, the first version will be called.


It is possible for the return type of a function template to depend on the types of the template parameters. In your case, you can do something similar to:

template <typename L, typename R>
struct sum_traits { typedef double return_type; };

template <>
struct sum_traits<int, int> { typedef int return_type; };

template <typename L, typename R>
typename sum_traits<L, R>::return_type
sum(L l, R r) { 
  typedef typename sum_traits<L, R>::return_type ret_t;
  return ret_t(l) + ret_t(r); 
}

I don't think the explicit casts to ret_t are ever actually needed in this case, but it demonstrates some more of the technique.

This handles just ints, but the idea can easily be generalized to handle more complex cases.


This might be what you need:

#include <iostream>
using namespace std;

template <class input1, class input2, class output> output add(input1 n1, input2 n2) {
   return (output) n1 + (output) n2;
}

int main(int argc, char **argv) {

   cout << add<int, int, int>(1,1) << endl;
   cout << add<float, int, float>(1.1f,1) << endl;
   cout << add<int, float, float>(1,1.1f) << endl;
   cout << add<float, float, int>(1.1f,1.1f) << endl;

   return 0;
}

Result:

quad: > ./a.out 
2
2.1
2.1
2
Sun 09 Jan 2011 12:57:57 PM MST

quad: > 


The answer to your question lies in Chapter 15 of C++ templates book. This chapter has an accumulator example which addresses your question. Further down the chapter it will talk about promotion traits where it will address the problem of adding two different types and also address type promotion.

0

精彩评论

暂无评论...
验证码 换一张
取 消