在@interface中声明ivar和在@implementation中放置变量之间的区别

nic*_*fox 7 scope class objective-c variable-declaration

在一个.m文件中声明一个ivar @interface与一个变量之间的区别是什么@implementation

@interface MyClass : NSObject {
  int num;
}
- (void)doSomething;
@end
Run Code Online (Sandbox Code Playgroud)

@implementation MyClass   
int num2;

- (void)doSomething {
  num = 137;
  num2 = 138;
}
@end
Run Code Online (Sandbox Code Playgroud)

有没有时间你想把变量放在@implementation

dre*_*wag 8

使用ivar和在实现中声明变量之间的区别在于实现中的变量位于文件范围和全局.这意味着所有实例(和任何静态方法)将共享同一个变量; 即如果对象的一个​​实例更改了变量,它将为所有实例更改它.

在文件范围定义它的用例是为静态方法存储内容(直接作用于类而不是类的实例的方法).一个真正常见的用例是Singleton设计模式.您可以在此文件中定义类的静态实例,以便您可以随时确保访问同一实例.您可以提供一个返回此实例的静态方法,以便代码中的任何对象都可以通过直接在类上调用该方法来访问该对象.

2014年4月17日更新

现在常见的做法是使用Properties.这会为您创建getter和setter,自动使类更具可扩展性(如果您决定更改属性的工作方式,也许您希望将其更改为始终即时计算,则类的公共接口无需更改).

您可以使用私有类扩展来声明"私有"属性和方法.这具有保护某些属性和方法不被外部类访问的效果.


Ton*_*ony 5

据我所知,在@implementation中放置一个变量声明与将它放在实现之外没什么不同:它不是一个ivar,它只是一个在文件范围内声明的变量.

一个用途是声明C++静态成员的等价物.例如:

@implementation MyClass

static int s_count = 0;

- (id)init {
  if ((self = [super init]))
    ++s_count;
  return self;
}

- (void)dealloc {
  --s_count;
  [super dealloc];
}
Run Code Online (Sandbox Code Playgroud)

假设init您是唯一的初始化程序,那么s_count将包含MyClass活动的实例总数.

  • @nickfox _Global variables_,static或not,与程序具有相同的生命周期,可以被实现文件中的任何方法或函数使用,这就是它们可以用作类变量的原因.非静态全局变量_也可以由其他实现文件使用,类似于公共类变量._static全局变量_只能由声明它的实现文件使用,因此充当私有类变量. (5认同)
  • 即,静态全局变量可以用作类变量. (2认同)
  • 我只是和一些人谈论它,他们说ivar是一个实例变量,而@implementation中声明的变量是"全局的,就像不是每个实例".听起来像静电的我.我得到了ivar的内容,但仍然不清楚@implementation中的变量以及何时应该使用它. (2认同)