c++ - 模板函数中的名称查找规则

标签 c++ c++11 templates

#include <iostream>
using namespace std;

template<typename T>
void adl(T)
{
  cout << "T";
}

struct S
{
};

template<typename T>
void call_adl(T t)
{
  adl(S());
  adl(t);
}

void adl(S)
{
  cout << "S";
}

int main ()
{
  call_adl(S());
}

为什么结果是“TS”?模板函数中的名称查找规则是什么?

http://ideone.com/sB3DnL

最佳答案

模板的编译分为两个阶段,即定义点和实例化点。第一阶段发生在编译器首次处理模板定义时,一些名称立即绑定(bind)到定义。有些名称在模板实例化之前是未绑定(bind)的,因为它们依赖于模板参数,因此在模板实例化并且模板参数已知之前无法查找。

在这个调用中:

adl(S());

没有任何依赖函数的模板参数,所以查找立即完成(在第一阶段),它找到了唯一一个名为 adl 的函数。这在当时的范围内。

在这个调用中:

adl(t);

依赖于 t 的类型所以当 t 的类型时,查找被延迟到实例化时众所周知。当您调用 call_adl(S()) adl 的第二次重载在范围内,所以当 adl(t)调用执行名称查找,范围内还有另一个函数,它更适合参数。

关于c++ - 模板函数中的名称查找规则,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/42729586/

相关文章:

c++ - 为什么我收到 "no matching function"错误?

c++ - 在for循环中计算复利

c++ - 在什么情况下会在这种情况下执行死刑?

c++ - 函数模板 : default first template argument to second

c++ - 使用模板插入函数丢失数字

c++ - 为什么在 main() 中声明的指针没有改变?

c++ - 重载类本身

c++ - 为什么move构造函数不通过using声明继承

c++ - 返回 nullptr 迭代器,如何转换它们

c++ - 模板函数的歧义递归定义