Objective-C和objective-C++中静态成员的定义

The*_*One 6 static compilation objective-c objective-c++ redefinition

编译objective-c源代码和objective-c ++源代码时,我有所不同.

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

#import <Foundation/Foundation.h>

@interface Class1 {
}
@end

@interface Class2 {
}
@end
Run Code Online (Sandbox Code Playgroud)

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

#import "test.h"

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


@implementation Class2
/* static member */
static int mystatic;
@end
Run Code Online (Sandbox Code Playgroud)

我用这个命令成功编译:

gcc -arch armv6 -isysroot /Developer/.../iPhoneOS5.0.sdk -x objective-c -c test.m
Run Code Online (Sandbox Code Playgroud)

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

#import "test.h"

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


@implementation Class2
/* static member */
static int mystatic;
@end
Run Code Online (Sandbox Code Playgroud)

并使用此命令行进行编译(-x选项中的差异):

gcc -arch armv6 -isysroot /Developer/.../iPhoneOS5.0.sdk -x objective-c++ -c test.mm
Run Code Online (Sandbox Code Playgroud)

但是我收到一个错误:

test.mm:11 error: redefinition if 'int mystatic'
Run Code Online (Sandbox Code Playgroud)

为什么我在ObjC++中而不是在ObjC中出现此错误?

das*_*ght 6

这归结为C和C++之间的差异.在C中,可以重新定义具有相同名称和相同类型的静态变量; 在C++中,做同样的事情是一个错误.

从C标准:

具有没有初始化程序的文件范围且没有存储类说明符或存储类说明符静态的对象的标识符声明构成暂定定义.如果翻译单元包含一个或多个标识符的暂定定义,并且翻译单元不包含该标识符的外部定义,则行为就像翻译单元包含该标识符的文件范围声明一样,复合类型为翻译单元的结尾,初始化程序等于0.

从C++标准:

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

int i ;
int i ;
Run Code Online (Sandbox Code Playgroud)

在C中有效,[但它在C++中无效].

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