Objective-c下变量和属性的区别

简介: 随着苹果将默认的编译器从GCC换成了LLVM,编译器自动为一个属性生成对应的变量和setter/getter方法,我们已经越来越习惯在自己创建的类中直接通过声明一个属性来创建一个类变量了。比如: #import <Foundation/Foundation.h>@interface Person : NSObject@property (nonatomic, st

随着苹果将默认的编译器从GCC换成了LLVM,编译器自动为一个属性生成对应的变量和setter/getter方法,我们已经越来越习惯在自己创建的类中直接通过声明一个属性来创建一个类变量了。比如:

#import <Foundation/Foundation.h>

@interface Person : NSObject

@property (nonatomic, strong) NSString* name;
@property (nonatomic) int age;

-(void)func;
-(instancetype)init;
-(void)setName:(NSString *)name;
-(NSString*) name;
@end

但是却忽视了属性和变量本质上的区别,导致在使用中遇到很多奇怪的问题无法理解,尤其是在非ARC下这种情况就更是如此。

在最早的iOS编程中,我们必须为每一个属性声明一个对应的变量,两者相互配合使用,比如:

@interface MyViewController :UIViewController
{
    UIButton *myButton;
}
@property (nonatomic, retain) UIButton *myButton;
@end

但是现在我们并不需要这么写,只需要声明一个属性比如name,那么编译器就会自动为其声明一个对应的变量_name。在我看来,所谓属性,其实本质还是对变量的管理,属性可以看做是对变量的封装,通过封装变量一来可以方便开发,省略了大量的setter/getter方法的编写。同时也避免了直接操作变量的不安全性。在此基础之上,属性还有多个附加特性:nonatomic、strong、weak、copy、atomic等等,使得原本复杂的线程安全、retain/release机制等都可以通过简单的属性申明而避免,大大方便了程序开发。由此看来,属性确实是Objective-c相对于其他语言一个重要的优势。


变量

Objective-c下传统的变量并没有太多的区别:公有、私有以及保护变量:
#import <Foundation/Foundation.h>

@interface Person : NSObject
{
@private
    int privateVar;
@public
    int publicVar;
@protected
    int protectedVar;
}

@end

其含义和C++、Java等语言也一样:公有变量可以在类外部访问;私有变量仅能在类内部访问且不能被子类访问;保护变量仅能在类内部和子类访问。在Objective-c中访问类变量的语法是:self->privateVar。注意必须要使用类似C++下指针的访问方式,如果使用.语法是无法访问变量的。使用诸如self->privateVar的语法访问变量就是直接操作变量,这时变量操作的安全性都是由编码者自己负责。尤其是在操作涉及到内存操作的时候需要格外小心,最典型的使用场景就是在对诸如NSString*等类型的变量进行赋值操作时候的retain和release操作:
-(void)setPrivateVar:(NSString*)var
{
    if(self->privateVar == var)
        return;
    [var retain];
    [self->privateVar release];
    self->privateVar = var;
    return;
}

点语法

还有一点值得注意的就是,在使用属性之后,编译器不仅为对应的变量自动生成setter/getter方法,同时还简化了调用两种方法的方式:点语法。在Objective-c中p.name = @"liyazhou",这样一个语句并不是像在c++或者java下直接操作一个实例的类成员变量,而实际上是调用了对应的setter方法,所以p.name = @"liyazhou"调用的语句是[p setName:@"liyazhou"]。而return p.name实际上等价于return [p getName];

以上就是Objective-c下面属性和变量最基本的区别和联系。总的来说属性的出现大大简化了Objective-c的编程,但同时也使初学者混淆了相关概念,稀里糊涂之下随便使用,知其然不知其所以然,遇到问题不知所措。所以想要放心大胆地使用一些便利而强大的编程特性就必须对其背后的原理烂熟于胸才行。
相关文章
|
存储 iOS开发 开发者
追根问底:Objective-C关联属性原理分析
Objective-C是一种动态性很强的语言,所谓动态能力,也可以理解为运行时能力。对于Objective-C开发者来说,动态性所带来的编程便利无处不在。例如通过Category类别来扩展已有类的功能。可以使已有类拥有新的方法和属性。
174 0
|
iOS开发
Objective-C中通过下标的方式访问自定义数据模型中属性
Objective-C中通过下标的方式访问自定义数据模型中属性
153 0
|
iOS开发
Objective-C 中变量的作用域
Objective-C 中变量的作用域
141 0
|
iOS开发 编译器 安全
|
iOS开发 安全
《Effective Objective-C 2.0》4、Objective-C类的属性
1、属性——property Objective-C的属性用于封装对象之中的数据,其作用同类的数据成员类似,但是所起到的作用远远大于普通的数据成员。
943 0
|
iOS开发
Objective-c官方文档 封装数据属性
版权声明:原创作品,谢绝转载!否则将追究法律责任。   很多对象需要跟踪信息为了执行他们的任务。一些对象设计模型一个或者多个值。例如NSNumber 类用来保存一个值或者自定义的类有一些属性。有一些对象不在一般的范围内。
972 0
|
程序员 iOS开发
Objective-c为什么要有属性
属性:为什么要有属性 。 首先是因为实例变量的安全性和继承能力,如果我们允许被继承,子类要动这些实例变量,我们需要能够参与进来,如果子类设置了某个值,我们需要检查范围,保证不会破坏父类,保证不会破坏父类,所以这是要有属性的首要原因。
689 0
|
iOS开发
Objective-C 属性特性(assign , retain , copy , readonly , readwrite , atomic , nonatomic)
文档地址:Property Declaration Attributes section of the Objective-C Programming Language assign:指定setter方法用简单的赋值,这是默认操作。
804 0