5

ISO C++ 草案 (n3290) 中的一点:

3.4.2/3 参数依赖名称查找:

X是由非限定查找(3.4.1)Y生成的查找集,让 是由参数相关查找(定义如下)生成的查找集。如果X包含

  • 类成员的声明(#1)或
  • 不是使用声明(#2)的块范围函数声明或
  • 既不是函数也不是函数模板的声明(#3)

然后Y是空的。否则Y是在与参数类型关联的命名空间中找到的一组声明,如下所述。通过名称查找找到的声明集是和 的X并集Y

是否有演示涉及#1、#2 和#3 的 ADL 的示例代码片段?

4

3 回答 3

3

我认为这段代码涵盖了所有情况(也可在http://ideone.com/CbyJv获得)。如果您没有在 ideone 中选择 C++0x,那么情况 #2 是允许的(但 gcc 4.5.2 会捕获它)。

#include <iostream>

// ::f
void f (int i) { std::cout << "::f\n" ; }

// Simple case
void OK1() {
  f (99) ; // Calls ::f
}

// Argument-dependend lookup
namespace MyNamespace {
struct S { int i ; } ;
void f (S& s) { std::cout << "MyNamespace::f\n" ; }
}

void OK2() {
  MyNamespace::S s ;
  f (99) ;   // Calls ::f
  f (s) ;    // Calls MyNamespace::f because the type of s is declared in MyNamespace
}

// Declaration of a class member (#1)
struct C {
  static void ERROR1() {
    MyNamespace::S s ;
    f (s) ;        // Error: MyNamespace::f not matched, because Y is empty (#1)
  }
  static void f() { // Declaration of a class member (#1)
    std::cout << "C::f\n" ;
  }
} ;

// Block-scope function declaration (#2)
void ERROR2() {
  void f() ; // Block-scope function declaration (#2)
  MyNamespace::S s ;
  f (s) ;    // Error: MyNamespace::f not matched, because Y is empty (#2)
}

// Declaration that is neither a function or a function template (#3)
void ERROR3() {
  MyNamespace::S s ;
  f (s) ;            // OK: MyNamespace::f called
  typedef int f[3] ; // Declaration that is neither a function or a function template (#3)
  f (s) ;            // Error: MyNamespace::f not matched, because Y is empty (#3). This is an initialiser
}
于 2011-08-03T12:31:45.993 回答
1

数字 1 非常简单 - 如果您在类中查找名称 N,并且该类有一个成员 N,就是这样!你不必去其他地方寻找。

2号我相信是相似的,但在一个街区内

{
    void f(double);

    f(42);
}

如果可能,代码将尝试调用在那里声明的函数 f,否则放弃。

3 号再次相似。如果您查找名称 N 并找到具有该名称但不是函数的东西,您不必去寻找重载。

于 2011-08-03T07:50:05.990 回答
0

对于它的价值,这也称为 Koenig 查找。我手头没有所有 3 个示例,但 Bo Persson 已经提供了一些示例。

于 2011-08-03T08:06:54.177 回答