在使用指针时,const以何种方式干扰标记更专业的模板

In what way const is interfering with marking a more specialized template when using pointers?

本文关键字:干扰 方式 指针 何种 const      更新时间:2024-05-10

我有这个工作代码:

template <typename X, typename Y>
auto f(X a,  Y b) { return a + b; };
template <typename X, typename Y>
auto f(X* a,  Y* b) { return *a + *b; };
int main() {
int* p;
int* q;
f(p, q);
}

它编译并运行第二f(),因为它更专业。

然而,如果我们const-限定这样的参数:

template <typename X, typename Y>
auto f(const X a, const Y b) { return a + b; };
template <typename X, typename Y>
auto f(const X* a, const Y* b) { return *a + *b; };
int main() {
int* p;
int* q;
f(p, q);
}

它不再工作,并尝试选择第一个函数,在指针的a + b上出错。

为什么const-限定类型会使第二个模板不再更加专业化?

为什么const限定类型使第二个模板不再更加专业化?

没有

";"问题";我们在这里观察到的是,在检查什么类型更专业之前,重载解析会考虑一些因素。

阅读部分最佳可行函数,我们可以看到:

对于每对可行函数F1和F2,对从第i个参数到第i个参数的隐式转换序列进行排序,以确定哪一个更好(除了第一个参数,静态成员函数的隐式对象参数对排序没有影响(

如果F1的所有自变量的隐式转换不比F2[…]的所有自变量隐式转换差,则F1被确定为比F2更好的函数

现在让我们看看这两个重载:

template <typename X, typename Y>
auto f(const X a, const Y b) { return a + b; };
int main() {
int* p;
int* q;
f(p, q);
}

这里是CCD_ 8和CCD_。无需转换。值得指出的是,ab的类型不是const int*,而是int* const

现在让我们来看看第二个过载:

template <typename X, typename Y>
auto f(const X* a, const Y* b) { return *a + *b; };
int main() {
int* p;
int* q;
f(p, q);
}

这里,为了从int*(即pq的类型(获得const int*(所需的自变量类型(,必须将XY推导为int*,然后必须进行转换。这是因为const int*并不意味着指向intconst指针,而是指向const int指向const int的指针和指向int的指针不相同,但后者可以转换为前者。在这种情况下,CCD_ 27和CCD_。

因此,过载解析会选择转换较少的候选者。该重载试图添加两个指针,结果导致编译时错误。