用作模板参数的局部类型
优质
小牛编辑
127浏览
2023-12-01
在C++98中,局部类和未命名类不能作为模板参数,这或许是一个负担,C++11则放宽了这方面的限制:
void f(vector<X>& v)
{
struct Less {
bool operator()(const X& a, const X& b)
{ return a.v<b.v; }
};
// C++98: 错误: Less是局部类
// C++11: 正确
sort(v.begin(), v.end(), Less());
}
当然除了这里的局部类之外,在C++11中,我们还可以采用Lambda表达式来做同样的事情:
void f(vector<X>& v)
{
sort(v.begin(), v.end(),
[] (const X& a, const X& b) { return a.v<b.v; });
}
尽管如此,我们仍然不要忘记,为一系列动作行为命名有利于文档化,是一个值得鼓励的设计风格。而且,非局部的函数体(当然也需要命名)还可以被重用于其他模块。
C++11同时也允许模板参数使用未命名类型的值:
template<typename T> void foo(T const& t){}
enum X { x };
enum { y };
int main()
{
foo(x); // C++98: ok; C++11: ok
//(译注:y是未命名类型的值,C++98无法从这样的值中推断出函数模板参数)
foo(y); // C++98: error; C++11: ok
enum Z { z };
foo(z); // C++98: error; C++11: ok
//(译注:C++98不支持从局部类型值推导模板参数
}
参考:
- Standard: Not yet: CWG issue 757
[N2402=07-0262] Anthony Williams:
[N2657] John Spicer: