具有相同名称但不同范围(例如 foo、bar::foo)的命名空间如何工作?
How do namespace's with same name but different scope (e.g. foo, bar::foo) work?
如果有两个命名空间Foo
和Bar
,并且Bar
里面有一个命名空间Foo
。如果我从 Bar
中引用变量 Foo::i
,它将在 Foo
和 Bar::Foo
中搜索 i
。如果不是,当 Bar::Foo
中不存在 i
时,是否可以让编译器在两个命名空间中进行搜索?
更具体地说,在下面的示例中,我尝试从命名空间 a 中引用变量 i
,而不是添加额外的 ::
。我知道放置 ::
是可行的,我正在尝试查看是否有任何其他方法可以解决此问题。
#include <iostream>
#include <string>
namespace a {
int i = 1;
}
namespace b {
namespace a {
}
namespace c {
int j = a::i; // Doesn't work, need to use ::a::i;
}
}
int main()
{
std::cout << b::c::j << "\n";
}
您可以在内部命名空间中显式声明要从外部命名空间使用的变量的 using
声明。
即对于您的示例,
namespace a {
int i = 1;
}
namespace b {
namespace a {
using ::a::i; //inner one does not define its own
int i2 = 2; //inner one creates its own variable
}
namespace c {
int j = a::i; // Doesn't work, need to use ::a::i;
}
}
参见:
https://en.cppreference.com/w/cpp/language/namespace#Using-declarations
如果您可以更改 b::a
,那么您确实可以将 b::a
中的某些声明从 ::a
中用作后备:
namespace a {
int i = 1;
int j = 2;
}
namespace b {
namespace a {
namespace detail {
using ::a::i; // Selectively bring declarations from ::a here
}
using namespace detail; // Make the names in detail available for lookup (but not as declarations).
//int i = 2;
}
namespace c {
int j = a::i; // Uses ::a::i
// int k = a::j; // ERROR! We didn't bring ::a::j into b::a at all
}
}
取消注释 b::a::i
的声明将更改输出。由于正确的声明优先于命名空间 using 指令引入的名称。
如果有两个命名空间Foo
和Bar
,并且Bar
里面有一个命名空间Foo
。如果我从 Bar
中引用变量 Foo::i
,它将在 Foo
和 Bar::Foo
中搜索 i
。如果不是,当 Bar::Foo
中不存在 i
时,是否可以让编译器在两个命名空间中进行搜索?
更具体地说,在下面的示例中,我尝试从命名空间 a 中引用变量 i
,而不是添加额外的 ::
。我知道放置 ::
是可行的,我正在尝试查看是否有任何其他方法可以解决此问题。
#include <iostream>
#include <string>
namespace a {
int i = 1;
}
namespace b {
namespace a {
}
namespace c {
int j = a::i; // Doesn't work, need to use ::a::i;
}
}
int main()
{
std::cout << b::c::j << "\n";
}
您可以在内部命名空间中显式声明要从外部命名空间使用的变量的 using
声明。
即对于您的示例,
namespace a {
int i = 1;
}
namespace b {
namespace a {
using ::a::i; //inner one does not define its own
int i2 = 2; //inner one creates its own variable
}
namespace c {
int j = a::i; // Doesn't work, need to use ::a::i;
}
}
参见: https://en.cppreference.com/w/cpp/language/namespace#Using-declarations
如果您可以更改 b::a
,那么您确实可以将 b::a
中的某些声明从 ::a
中用作后备:
namespace a {
int i = 1;
int j = 2;
}
namespace b {
namespace a {
namespace detail {
using ::a::i; // Selectively bring declarations from ::a here
}
using namespace detail; // Make the names in detail available for lookup (but not as declarations).
//int i = 2;
}
namespace c {
int j = a::i; // Uses ::a::i
// int k = a::j; // ERROR! We didn't bring ::a::j into b::a at all
}
}
取消注释 b::a::i
的声明将更改输出。由于正确的声明优先于命名空间 using 指令引入的名称。