为什么大多数实现在C ++ 03中的全局命名空间中仍然具有cmath函数?

时间:2016-02-20 09:56:14

标签: c++ namespaces

据我了解,在C ++ 03中#include <cmath>必须仅在namespace std中声明这些函数。从C ++ 11开始,它们还可以在全局命名空间中声明。这是大多数C ++实现在全局命名空间中声明函数的实践的结果(可能是#include ing <math.h>),然后在using ::acos;中只是namespace std等。

但在我看来,实现在<cmath>中执行类似的操作同样容易:

namespace __C_LANGUAGE_MATH_H
{
#include <math.h>
}
// ...
namespace std
{
// ...
using __C_LANGUAGE_MATH_H::acos;
// ...
}

为什么不实践这一点而不仅仅是污染全局命名空间?我建议的解决方案是否有一些主要缺点使得C ++委员会允许在C ++ 11中污染全局命名空间?

注意:这确实有效,并且链接器没有错误,至少对于GCC + Binutils-ld。我实际上已经尝试并编辑了GCC的cmath文件,如下所示,并编译了我的项目,该项目成功地主动使用cmath函数(在修复了一些错误未在项目中指定std::的调用之后):

mv /usr/include/c++/5.3.0/cmath{,.bak}
sed -i -e 's@\(# *include <math.h>\)@namespace __C_LANGUAGE_MATH_H\n{\n\1\n}@' \
    -e 's@\(using \+\)::@\1__C_LANGUAGE_MATH_H::@' /usr/include/c++/5.3.0/cmath

2 个答案:

答案 0 :(得分:2)

正如gcc bugzilla中相应的问题discussion中所述,由于包含警卫,这种方法不允许在C ++之后包含C头:

#include <cmath>
#include <math.h> // include skipped by include guards

...
sin(x); // error: no sin in global namespace

正如您所提到的,C库包装器的标准要求在defect report中发布问题后发生了更改,并且从实现的角度来看,之前的要求已被宣布为不切实际。

答案 1 :(得分:-1)

他们不这样做,因为它不起作用。试试吧。名为__C_LANGUAGE_MATH::acos的C库中没有任何功能。