成员变量和属性的区别

    作为一个iOS的开发者,相信大家都知道由@property声明的属性默认会生成一个成员变量,同时也会为其生成setter/getter方法。 

例1:

@property (nonatomic,copy) NSString * name;

在对应的.m文件中,编译器会为该属性自动的生成一个成员变量_name。
同时也会生成其对应的setter/getter方法。

我们在.m文件中可以不仅可以直接使用_name成员变量,也可以通过属性self.name来使用该属性。

事实上,这只是iOS5之后(新编译器LLVM)的新机制。在之前(老编译器GCC),是需要我们手动完成一系列操作:**在一个大括号里面定义成员变量,同时不仅需要用@property声明,还需要在@implementation中使用@synthesize方法修饰该属性。
**

例2:
@interface ViewController ()
{
// 第一步:声明成员变量
NSString * name;
NSString * password;
}
//第二步:定义一个属性
@property(nonatomic, copy) NSString *name;
@end
@implementation ViewController
/*第三步:
最后在@implementation中用synthesize为属性生成setter/getter方法
@synthesize 属性名称 = 成员变量名称;
**当等号两边的值一致时,可省略等号及等号右边内容。
*/
@synthesize name ;
@end

`
竟然需要经历如此繁琐的步骤,我们才生成一个看似和新编译器一样的属性name。
“三部曲”中,第三步事实上绑定了属性和成员变量,这决定了 setter和getter方法的内部实现。假设我们把第三步写为@synthesize name = password时,我们通过.name 获得值或者对其进行赋值,其实都是在对password作用。可参考如下代码:

例3:

@interface ViewController ()
{
    NSString * name;  
     NSString * password;  
 }
 
@property(nonatomic, copy) NSString *name;  

@end

@implementation ViewController

@synthesize name = password;   

- (void)viewDidLoad {

    [super viewDidLoad];
    self.name = @"shimanfei";//为password赋值
    NSLog(@"%@",name);//null  
     NSLog(@"%@",self,name);// 打印结果为:shimanfei  -- 读取password中的值
    NSLog(@"%@",password);//shimanfei
    self.name = @"guochengjie";
     NSLog(@"%@",name);//null 
     NSLog(@"%@",self.name);// 打印结果为:guochengjie -- 读取password中的值
    NSLog(@"%@",password);// guochengjie
    name = @"test";
    NSLog(@"%@",name);// test 
    NSLog(@"%@",_name);// 报错,显示没有该实例对象
    
}


/*
编译器默认为我们实现的setter/getter方法
-(void)setName:(NSString *)name{
    password = name;
}
-(NSString*)getName{
    return password;
}
*/
@end

以上说明:
a.当synthesize name 与其他成员变量(password)绑定之后,与它同名的成员变量(name)还是一个普通的成员变量,与setter和getter无关。
b.“三部曲”方式并未额外给类生成与属性对应的成员变量,仅仅是原本的成员变量参与到了属性的setter/getter方法。与此对比,新的编译器确实为该类生成了一个“_属性名称” 这样一个成员变量,并实现了对应的setter/getter方法。

那么现在我们想一下,我们能否认为新编译器下的@property 就完全等同于老编译器下的“三部曲”结果呢? 结果当然是不了!

现在我们回过头来看属性和成员变量到底是否是什么?
其实它们两个只是两个不同的概念。属性对应的一定有setter/getter方法,主要是对成员变量赋值/获取值的。而成员变量,则真的是一个变量。
例1中的name是该类的属性,_name是成员变量。
例2中的name是该类的属性,name(和属性同名)、password是成员变量。
例3中的name就是该类的属性,name(和属性同名)、password是成员变量。

  • 1
    点赞
  • 2
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值