标准库不会为重复定义引发错误
standard library not raising error for duplicate definition
为什么这不是 return 重复函数定义的错误,因为 c++ 标准库进行外部链接。
这不应该是函数重载,因为它是 double(double,double) 类型,与 math.h
中定义的 pow 完全相同
#include <iostream>
#include <math.h>
double pow(double base, double exponent) {
return 1;
}
int main() {
std::cout << pow(2, 2);
}
函数签名pow(double, double)
保留给全局命名空间中的语言实现。通过定义保留名称,程序的行为是未定义的。
那么程序的行为是未定义的,你不能保证会“为重复定义引发错误”。
相关标准规则(来自最新草案):
[reserved.names.general]
If a program declares or defines a name in a context where it is reserved, other than as explicitly allowed by [library], its behavior is undefined.
[extern.names]
Each name from the C standard library declared with external linkage is reserved to the implementation for use as a name with extern "C" linkage, both in namespace std and in the global namespace.
Each function signature from the C standard library declared with external linkage is reserved to the implementation for use as a function signature with both extern "C" and extern "C++" linkage, or as a name of namespace scope in the global namespace.
Why does this not return an error for duplicate function definition...?
因为C库提供的pow
的定义不需要在包含的头文件中。此头文件 (math.h
) 可能仅包含其声明。在这种情况下,生成的翻译单元可能如下所示:
...
double pow(double, double);
...
double pow(double base, double exponent)
{
return 1;
}
int main()
{
std::cout << pow(2, 2);
}
这个翻译单元绝对没有问题。但是,问题发生在 linking 期间,因为 linker 可以 link 你的 pow
在机器代码级别调用两个不同的函数——由C 库和其他由翻译单元创建的目标文件提供的。
linker 实际要做的事情并没有被 C++ 标准定义。它只是说您的代码的行为未定义。
为什么这不是 return 重复函数定义的错误,因为 c++ 标准库进行外部链接。
这不应该是函数重载,因为它是 double(double,double) 类型,与 math.h
中定义的 pow 完全相同#include <iostream>
#include <math.h>
double pow(double base, double exponent) {
return 1;
}
int main() {
std::cout << pow(2, 2);
}
函数签名pow(double, double)
保留给全局命名空间中的语言实现。通过定义保留名称,程序的行为是未定义的。
那么程序的行为是未定义的,你不能保证会“为重复定义引发错误”。
相关标准规则(来自最新草案):
[reserved.names.general]
If a program declares or defines a name in a context where it is reserved, other than as explicitly allowed by [library], its behavior is undefined.
[extern.names]
Each name from the C standard library declared with external linkage is reserved to the implementation for use as a name with extern "C" linkage, both in namespace std and in the global namespace.
Each function signature from the C standard library declared with external linkage is reserved to the implementation for use as a function signature with both extern "C" and extern "C++" linkage, or as a name of namespace scope in the global namespace.
Why does this not return an error for duplicate function definition...?
因为C库提供的pow
的定义不需要在包含的头文件中。此头文件 (math.h
) 可能仅包含其声明。在这种情况下,生成的翻译单元可能如下所示:
...
double pow(double, double);
...
double pow(double base, double exponent)
{
return 1;
}
int main()
{
std::cout << pow(2, 2);
}
这个翻译单元绝对没有问题。但是,问题发生在 linking 期间,因为 linker 可以 link 你的 pow
在机器代码级别调用两个不同的函数——由C 库和其他由翻译单元创建的目标文件提供的。
linker 实际要做的事情并没有被 C++ 标准定义。它只是说您的代码的行为未定义。