Pre*_*rag 10 c++ templates c++11
有人可以解释为什么这两个专业化对编译器来说难以区分(gcc 4.5.1 @ ideone)
template <typename... T> struct S;
template<typename A, typename B, typename... C>
struct S<A, B, C...> {
int f() {return 1;}
};
template<typename... A, typename... C>
struct S< S<A...>, C...> {
int f() {return 2;}
};
Run Code Online (Sandbox Code Playgroud)
当我尝试实例化 S<S<a, b>, a, b> o2;
编译器抱怨时:
prog.cpp:20:21: error: ambiguous class template instantiation for 'struct S<S<a, b>, a, b>'
prog.cpp:6:22: error: candidates are: struct S<A, B, C ...>
prog.cpp:11:33: error: struct S<S<A ...>, C ...>
prog.cpp:20:21: error: aggregate 'S<S<a, b>, a, b> o2' has incomplete type and cannot be defined
Run Code Online (Sandbox Code Playgroud)
当最后一个专业化改为:
template<typename... A, typename B, typename... C>
struct S< S<A...>, B, C...> {
int f() {return 2;}
}
Run Code Online (Sandbox Code Playgroud)
一切正常.
我对这个问题的理解:
typedef S<S<a, b>, c, d> S2;
Run Code Online (Sandbox Code Playgroud)
这里S<a,b>
更好地匹配第二个专业化.但是,c, d
对于第一个特化的剩余参数(单个arg +列表与列表)更好地匹配.因此它是1:1.
如果你在B
第二个专门化中发表评论,那么第二个专业化会更好地匹配,因为它更专门用于第一个参数(S<...>
),其余的同样好.
我弄得一团糟; 它现在应该没关系,但是归功于下面的@UncleBens谁做对了(并且应该得到"接受").
如果没有B
第三个版本,则有两个部分特化,在实例化时具有同样的特殊性S<S<X,Y,Z>, T1, T2, T3>
:
A = S<X,Y,Z>
,.B = T1
C... = T2, T3
B
:A... = X,Y,Z
, C... = T1, T2, T3
.B
:A... = X,Y,Z
,B = T1
,C... = T2, T3
.这不会在部分专业化排序中建立可比较的元素!
请注意,您可以说template <typename ...> struct S;
和template <typename A, typename ...B> struct S<A, B...>;
第二个比第一个更具体,因为它具有更多非可变参数.
但另一方面,没有B
,当你说S<S<X,Y,Z>,T1,T2,T3>
,那么第一个参数在第二个PS中匹配得更好,但其余参数在第一个PS中匹配得更好.随着B
到位,虽然第二个PS是更具体的.
与此相比,部分特那是实际上更具体:
template <typename ...A, typename B, typename ...C>
struct S<B, std::tuple<C...>, std::tuple<C...>> { /* ... */ };
Run Code Online (Sandbox Code Playgroud)
现在很清楚给定实例是匹配特化还是仅匹配一般形式.专门化具有固定数量的参数(3),因此它赢得了具有可变数量参数的另一个特化.
归档时间: |
|
查看次数: |
254 次 |
最近记录: |