使用命名空间对定义无效
using namespace does not work for definitions?
我在理解c++名称空间时遇到问题。考虑以下示例:
//distr.h
namespace bogus{
extern const int x;
extern const int y;
double made_up_distr(unsigned param);
}
现在,如果我定义我的变量,比如下面的cpp,所有的东西都会编译好
//distr.cpp
#include "distr.h"
#include <cmath>
const int bogus::x = 10;
const int bogus::y = 100;
double bogus::made_up_distr(unsigned param){
auto pdf = (exp(param) / bogus::x) + bogus::y;
return pdf;
}
但是,如果我尝试简单地引入bogus
名称空间并使用
//broken distr.cpp
#include "distr.h"
#include <cmath>
using namespace bogus;
const int x = 10;
const int y = 100;
double made_up_distr(unsigned param){
auto pdf = (exp(param) / x) + y;
return pdf;
}
我的编译器告诉我对x
和y
的引用是不明确的。为什么?
有一个简单的原因可以解释为什么这不能像你预期的那样工作:
namespace bogus {
const int x;
}
namespace heinous {
const int x;
}
using namespace bogus;
using namespace heinous;
const int x = 10;
现在,上面的x
应该指bogus::x
、heinous::x
还是新的全局::x
?这将是第三个没有using
语句的代码,这意味着添加using语句将以一种特别微妙的方式改变现有代码的含义。
using语句用于介绍查找的作用域(通常但不一定是命名空间)的内容。声明
const int x = 10;
通常一开始就不需要查找,除非检测到ODR违规。
声明/定义中的标识符的名称查找与使用中的名称查找不同。特别是,它不关心使用语句。原因很简单:如果情况不同,就会导致各种令人讨厌的惊喜。考虑一下:
// sneakattack.h
namespace sneakattack { void foo(); }
using namespace sneakattack;
// somefile.cpp
#include "sneakattack.h"
void foo() { std::cout << "Hellon"; }
// otherfile.cpp
void foo();
int main() { foo(); }
该程序当前有效:声明sneakattack::foo
被忽略,定义::foo
被正确地链接到其他文件中的使用。但是,如果名称查找的工作方式不同,某个文件会突然定义sneakattack::foo
,而不是::foo
,并且程序将无法链接。
相关文章:
- 在 Microsoft Access SQL 中调用自定义 DLL 函数时传递的内存地址无效
- 如何定义此"if block"中其他无效输入的值,以便在c ++中将字符串转换为对象?
- 使用无效指针初始化指针声明符的行为是否未定义?
- 用户定义的到右值引用的转换无效
- 最终说明符对单独的声明和定义无效
- 从参考中获取的指针可以在定义明确的C 中取无效
- 将流定义为私有类变量似乎在Linux下有效,但在WindowsVisualStudio下无效
- 如何在没有参数列表的情况下定义向量无效使用模板名称 std::vector
- 使用基类中定义的函数返回指向派生类实例的指针时发生无效转换错误
- “无效的操作数是二进制表达式”当使用自定义结构作为C 中的MAP索引时
- 对无效"function" C++的未定义引用
- 将成员枚举变量传递给类构造函数时出现无效的重定义错误
- 用户定义类中的Null指针无效
- 在自定义迭代器上应用reverse_iterator后引用无效
- 由于未定义的符号'start_time',MEX 文件无效
- Cpp.中的私有静态数据成员只能在其定义时初始化,而类内初始化无效
- 取消引用无效指针但不使用结果是否是C++中的未定义行为
- C++:对无效函数的未定义引用
- 在模板参数中定义类,为什么它无效
- 使用命名空间对定义无效