Traits偏特化:类模板部分特例化(partial specialization)
我们只能部分特例化类模板,而不能部分特例化函数模版。——《C++ Primer(5th)》 P628
1. 实现 Sigma 函数,功能是将一段范围内的元素求累加和。
2. 错误的代码实例:
template <typename T> T sigma(T* start, T* end) { T total = T(); while (start != end) total += *start++; return total; }
2.1 错误原因:
如果传入 char 类型范围(迭代器)“a b c”,理论上计算结果应该返回 294 ,也就是 0x0126 ,存储需要两个字节。但是 char 只有一个字节大小,所以会造成溢出。
实际输出结果为 38 ——也就是溢出之后的值。
3. 正确的代码,采用偏特化,针对不同的型别写出不同的对策——本例中“对策”是声明不同的内置型别来存储返回值类型。
template <typename T> class SigmaTraits {}; template<> class SigmaTraits <char> // 针对char型的对策 { public: typedef int returnType; }; template<> class SigmaTraits <int> // 针对int型的对策 { public: typedef int returnType; }; template <typename T> typename SigmaTraits<T>::returnType sigma(T* start, T* end) { typedef typename SigmaTraits<T>::returnType returnType; returnType total = returnType(); while (start != end) { total += *start++; } return total; }
4. 调用 sigma 函数的方法方式都是一样的。
4.1 char范围的调用实例:
char str[] = "abc"; cout << sigma(str, str + 3) << endl;
4.2 int范围的调用实例:
int arr[] = {1, 2, 3}; cout << sigma(arr, arr+3) << endl;
5. 总结
理解 traits 更像像是一种设计模式,类似于工厂方法:针对不同的型别,有不同的对策。
时间: 2024-10-11 04:18:12