gpt4 book ai didi

c++ - 全局未命名命名空间歧义与嵌套未命名命名空间歧义

转载 作者:太空狗 更新时间:2023-10-29 20:39:56 25 4
gpt4 key购买 nike

考虑以下两个代码片段:

Snippet A

#include <iostream>

namespace
{
bool foo = false;
}

bool foo = true;

int main()
{
std::cout << foo << std::endl;
}

Snippet B

#include <iostream>

namespace A
{
namespace
{
bool foo = false;
}

bool foo = true;
}

int main()
{
std::cout << A::foo << std::endl;
}

Snippet A , fooint main() 中的使用不明确,而在 Snippet B 中它不是。为什么会这样?


相关:Anonymous Namespace Ambiguity

最佳答案

未命名命名空间的行为在 §7.3.1.1 [namespace.unnamed]/p1 中指定:

An unnamed-namespace-definition behaves as if it were replaced by

inline_opt namespace unique { /* empty body */ }
using namespace unique ;
namespace unique { namespace-body }

where inline appears if and only if it appears in the unnamed-namespace-definition, all occurrences of unique in a translation unit are replaced by the same identifier, and this identifier differs from all other identifiers in the entire program.

特别注意,未命名命名空间内的声明通过 using-directive using namespace unique; 在周围范围内可见。

在片段 A 中,foo 是非限定的,因此编译器执行非限定名称查找(§3.4.1 [basic.lookup.unqual])。此处相关的是子条款的第 2 段:

2 The declarations from the namespace nominated by a using-directive become visible in a namespace enclosing the using-directive; see 7.3.4. For the purpose of the unqualified name lookup rules described in 3.4.1, the declarations from the namespace nominated by the using-directive are considered members of that enclosing namespace.

因此,非限定名称查找会找到 foo 的两个声明,并且名称不明确。

在代码段 B 中,A::foo 是限定的,因此适用限定名称查找规则。由于 A 是一个命名空间,适用的子条款是 §3.4.3.2 [namespace.qual]。与此处相关,该规则在该子条款的第 2 段中指定:

For a namespace X and name m, the namespace-qualified lookup set S(X,m) is defined as follows: Let S'(X,m) be the set of all declarations of m in X and the inline namespace set of X (7.3.1). If S'(X,m) is not empty, S(X,m) is S'(X,m); otherwise, S(X,m) is the union of S(Ni,m) for all namespaces Ni nominated by using-directives in X and its inline namespace set.

换句话说,仅当在指定命名空间及其内联命名空间集中找不到该名称时,限定名称查找才会考虑由 using-directives 指定的命名空间。这里,名称 foo 是在命名空间 A 中找到的,因此不考虑由 using-directive 指定的未命名命名空间,并且没有歧义.

如果您在代码段 A 中编写 ::foo 而不是 foo,则将应用合格的查找规则,并且再次不会出现歧义。

关于c++ - 全局未命名命名空间歧义与嵌套未命名命名空间歧义,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/26070916/

25 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com