4

我有两个模板函数:

template<class X> void foo(X a)
{
    cout << "Template 1" << endl;
}


template<class X> void foo(X *a)
{
    cout << "Template 2" << endl;
}

现在,如果我定义一个专业,例如:

template<> void foo<>(int *a)
{
    cout << "Specialization 1" << endl;
}

这个专业化属于模板 1 还是模板 2。另外,如果我在模板 2 之前或之后定义专业化,这有关系吗?

4

1 回答 1

2

替换Xint并查看哪个主模板产生匹配的签名:

template<class X> void foo(X a)

变成

template <> void foo<int>(int)

template<class X> void foo(X *a)

变成

template<> void foo<int>(int *)

因此,它只能是第二个功能的特化。由于该函数不特化第一个重载,因此有必要在定义特化之前声明第二个主模板,因为特化不能特化第一个主模板。

如果模板参数未在特化中明确指定,则使用根据 14.8.2.6 [temp.deduct.decl] 第 1 段的正常参数推导规则找到相关的主模板:

在其 declarator-id 指代函数模板的特化的声明中,执行模板参数推导以识别该声明所指的特化。具体来说,这是针对显式实例化 (14.7.2)、显式特化 (14.7.3) 和某些友元声明 (14.5.4) 完成的。

这个参数推导考虑了主模板的部分排序,即它找到了第二个主模板。我没有落入阅读导致打油诗的段落的陷阱,但警告是真实的:我认为如果您更改第二个主要模板的顺序和专业化,您会遇到麻烦!当心提到的自焚警告。

于 2013-08-17T00:32:07.673 回答