重新定义是否意味着我们正在尝试定义已定义的实体。此问题出现在以下代码示例中:
int a=5;
int main()
{
int a=3;//redefinition? I think no, because `int a` denote an entity different from the global "a"
}
还有一个例子:
int foo(){ return 1; }
int main()
{
int foo();
int a=foo();//Now a is 1
}
我们无法在foo()
函数体内定义声明的main()
函数,但是如果我们可以将其重新定义?
答案 0 :(得分:3)
局部变量可能会影响全局变量,这是::
范围解析运算符的用途
#include <iostream>
using namespace std;
int a=5;
int main()
{
int a=3;
cout << a; // 3
cout << ::a; // 5
}
这里没有ODR问题。
至于第二个例子,另一个函数内部的函数声明(当它没有被最烦恼的解析弄糊涂时),我推荐这个问题:Is there a use for function declarations inside functions?
而且:不,你可以在main()中重新定义你的功能。您可以重新声明它(即使使用不同的参数,因此声明一个新功能),但这并不意味着您可以定义它。
我推荐阅读wiki page的精彩摘录:
简而言之,ODR声明:
在任何翻译单元中,模板,类型,功能或对象都可以 只有一个定义。其中一些可以有任意数量 声明。定义提供了一个实例。
整个 程序,对象或非内联函数不能有多个 定义;如果使用了一个对象或函数,它必须只有一个 定义。您可以声明一个从未使用过的对象或函数, 在这种情况下,您不必提供定义。在任何情况下都不能 有不止一个定义。
有些东西,比如类型,模板, 和extern内联函数,可以在多个中定义 翻译单位。对于给定的实体,每个定义必须是 相同。非外部对象和函数在不同的翻译单元中 是不同的实体,即使它们的名称和类型相同。
编译器必须诊断某些违反ODR的行为。其他 违规,特别是那些跨翻译单位的违规行为,不是 需要被诊断出来。1
答案 1 :(得分:0)
没有。 int a = foo();
或int a = 3;
内的main()
是一个新变量,也称为a
。
重新定义是尝试重新定义相同的变量,例如:
int a = 5;
int a = 6;
另外
int foo();
不是定义。这是一个宣言。函数定义包括{ }
。
答案 2 :(得分:0)
不,在处理重新定义时,记住SCOPE非常重要。它仅适用于在SAME SCOPE中定义的两个具有相同名称的变量
在示例1中,第二个是LOCAL SCOPE并且是函数的本地。因此,在退出函数体
之前,这是查看和引用的a答案 3 :(得分:0)
第一个不是由于不同的范围而重新定义,就像你想的那样。
第二个是重新声明,但你可以随意重新发布任何次数,但这个笑话会随着重复而变得陈旧。
如果允许在函数内部定义函数,则可以编写所有语义,因为还有这样的语言(除了lambdas)。
对于这样做的人,请查看GCC C编译器,&#34;嵌套函数&#34;和&#34;语句表达式&#34;。
无论如何,由于一个定义规则,重新定义将是一个错误。
答案 4 :(得分:0)
重新定义有点导致编译时错误。 例如:
int a;
bool a;
或
void f();
int f;
在您的情况下,没有编译时错误。它涉及名称隐藏,范围和解决规则。
int a = 5;
{
int a = 6; //because of { } internal a is in other scope and can be defined without error
int b = a; //b == 6
}
int b = a; //b == 5
在最后一种情况下,你有两个不同的“a”,每个都在自己的程序范围内。 在程序的一个点上,如果使用诸如“a”的名称,则该名称后面只有一个实体。如果编译器找不到不同变体之间“a”的最佳匹配,则会得到重新定义和错误。