6

我在编译objective-c源和objective-c++源时有区别。

这里是 test.h 中 Class1 和 Class2 的声明:

#import <Foundation/Foundation.h>

@interface Class1 {
}
@end

@interface Class2 {
}
@end

现在,这是 test.m 中的 Objective-C 实现:

#import "test.h"

@implementation Class1
/* static member */
static int mystatic;
@end


@implementation Class2
/* static member */
static int mystatic;
@end

我用这个命令成功编译:

gcc -arch armv6 -isysroot /Developer/.../iPhoneOS5.0.sdk -x objective-c -c test.m

现在我完全使用了这个 Objective-C++ 实现 test.mm (完全相同的来源):

#import "test.h"

@implementation Class1
/* static member */
static int mystatic;
@end


@implementation Class2
/* static member */
static int mystatic;
@end

并使用此命令行编译(-x 选项不同):

gcc -arch armv6 -isysroot /Developer/.../iPhoneOS5.0.sdk -x objective-c++ -c test.mm

但我得到一个错误:

test.mm:11 error: redefinition if 'int mystatic'

为什么我在 ObjC++ 而不是 ObjC 中得到这个错误?

4

1 回答 1

6

这归结为C和C++之间的区别。在 C 中,可以重新定义具有相同名称和相同类型的静态变量;在 C++ 中,这样做是错误的。

来自 C 标准:

具有文件范围的对象的标识符声明没有初始化程序,并且没有存储类说明符或具有存储类说明符 static,构成暂定定义。如果翻译单元包含一个或多个标识符的暂定定义,并且翻译单元不包含该标识符的外部定义,则行为与翻译单元包含该标识符的文件范围声明完全相同,复合类型为翻译单元的末尾,初始化器等于 0。

从 C++ 标准:

C.1.2, 3.1 更改:C++ 没有 C 中的“暂定定义”。例如,在文件范围内,

int i ;
int i ;

在 C 中有效,但在 C++ 中无效。

就 Objective C 而言,该语言不支持在类级别作用域的变量;static int mystatic;在块内声明@implementation与在块外声明它的效果完全相同@implementation。要模拟类范围的变量,请在类方法中使用函数范围的静态变量。

于 2012-07-05T14:19:53.760 回答