【发布时间】:2011-05-19 15:37:51
【问题描述】:
考虑以下我的代码的简化版本。
我有一个模板类A,一个模板函数Fill,以及一个专门用于处理int 或char 等基本类型的函数,还有另一个专门用于处理A:
#include <sstream>
#include <string>
#include <iostream>
template<size_t C>
class A
{
public:
A & operator=(std::string v) {
data[0] ='a';
return *this;
}
char data[C];
};
template<typename T> T Fill(std::string value, T default_value);
// Specialization for A<C>
template<size_t C>
A<C> Fill(std::string value, A<C> default_value)
{
if (value.empty())
return default_value;
A<C> result;
result = value;
return result;
}
// Specialization for int, double, char, etc
template<typename T>
T Fill(std::string value, T default_value)
{
if (value.empty())
return default_value;
T result;
std::istringstream(value) >> result;
return result;
}
void main()
{
int abc = Fill(/*Get a string somehow*/"123", 0); // OK
A<10> def;
def = std::string("111");
A<10> a;
a = Fill(/*Get a string somehow*/"abc", def); // OK
}
虽然我很惊讶编译器设法将参数与正确的模板特化相匹配,但效果很好。
问题出现在一些typedefs 上,它们简化了A<x> 的使用。这是一个简化的版本:
typedef A<12> A12;
...
A<12> def12;
def12 = std::string("12");
A12 a12;
a12 = Fill(/*Get a string somehow*/"xyz", def12); // Not OK !
编译器没有检测到A12 类型实际上是A<12> 并使用了错误的函数特化,导致无法编译,因为 istringstream 无法将 operator>> 解析为A。
我怎样才能使它使用正确的模板专业化?
【问题讨论】:
-
第二个例子中的def是如何声明的?
-
函数模板不能被部分特化(而且你也没有使用特化语法),所以在你的例子中你实际上是在重载。
标签: c++ templates template-specialization