int bar = 2;
if (bar)
{
int bar;
}
gcc 或 Clang 都无法为此发出警告(或错误),并且程序在启动时立即崩溃。这有充分的理由吗?好像不是什么难抓的东西。这是 block 作用域的基础:嵌套作用域继承封闭 block 的名称...
有什么解释吗?
编辑:原来崩溃是由于使用 Clang。我来回测试了很多次,似乎可以肯定是变量重定义和 Clang 的组合导致了崩溃。但是,我无法在测试项目中重现崩溃,所以去看看吧。
问题原来是与 Objective-C 相关的。正如 Jonathan Leffler 指出的那样,在内部范围内执行“int bar = bar”会从自身初始化变量,这就是导致问题的原因,当初始化是通过 Objective-C 方法调用完成时。
下面显示了正在运行的错误:
-(void)crasher
{
NSNumber* bar = [NSNumber numberWithInt:2];
if (bar)
{
NSString* bar = [self doit:bar];
}
}
-(NSString*)doit:(NSNumber*)num
{
NSString* str = [num stringValue]; // This line causes the crash
return str;
}
请注意,在纯 C 中做类似的事情不会产生崩溃:
int bar = 2;
if (bar)
{
char buff[10];
int bar = sprintf(buff, "%d",bar);
}
最佳答案
这里没有什么可捕捉的。内部 block 中的变量是一个完全不同的变量,隐藏外部 block 中的变量。这是自古以来就存在的语言的完美标准功能。
您遇到的崩溃与您发布的代码完全无关。除非您在代码中犯了错误,否则在假设您正在使用外部变量的同时使用内部变量。
关于编译器无法捕获条件 block 中的变量重新定义,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/2388475/