objectcproperty括号内属性讲解

上传人:自*** 文档编号:79098336 上传时间:2019-02-16 格式:DOCX 页数:11 大小:53.39KB
返回 下载 相关 举报
objectcproperty括号内属性讲解_第1页
第1页 / 共11页
objectcproperty括号内属性讲解_第2页
第2页 / 共11页
objectcproperty括号内属性讲解_第3页
第3页 / 共11页
objectcproperty括号内属性讲解_第4页
第4页 / 共11页
objectcproperty括号内属性讲解_第5页
第5页 / 共11页
点击查看更多>>
资源描述

《objectcproperty括号内属性讲解》由会员分享,可在线阅读,更多相关《objectcproperty括号内属性讲解(11页珍藏版)》请在金锄头文库上搜索。

1、一、前言一个object的属性允许其他object监督和改变他的状态。但是在一个设计良好的面向对象程序中,直接访问一个object的内部状态是不可能的。相反,存取器(getter setter)方法是一个抽象相互作用object的底层数据。通过访问器方法与属性进行交互property指令的目标是通过自动的创建这些存取器方法使创建和配置属性变得更加简单。它允许你在语义级别上指定公有属性的行为。而且它比较关注你的详细实现。这个模型调查各种各样的属性,这些属性可以让你修改getter和setter行为。其中的一些属性确定是如何处理内存的,所以这个模型也服务于在Objective-C中对内存管理的实际

2、的介绍。二、property指令首先,让我们看一下当我们直接使用property时发生了什么事情,考虑一下下面的程序,一个Car类和它的实现。Car.h#import interface Car : NSObject property BOOL running;end Car.m #import Car.h implementation Car synthesize running = _running; /Xcode 4.4以上可选end编译器会为running属性创建一个getter和setter方法。默认的命名习惯是用属性自己作为getter,加上前缀set作为setter方法,并且在前

3、面加下划线作为实例变量,就像下面这样:-(BOOL)running return _running;-(void)setRunning:(BOOL)running _running = running;当用property直接生成属性,你可以直接调用这些方法,就像这些方法就是包含在该类的interface和实现文件中。你也可以在.m中重写他们,但是这样会使得synthesize指令强制。然而,你应该很少需要传统的存取器尽管property属性供这样做在抽象的级别。属性访问可以是用类实例后加.访问。所以看下面的代码:Car *honda = Car alloc init; honda.runni

4、ng = YES; NSLog(%d,honda.running);当执行honda.running时,也就是调用setRunning:方法。当给他分配值并且运行时,就是调用getter方法。为了改变这种存取器方式,我们可以在properry后加括号指定,下面就是介绍可用的属性。1、The getter= and setter= Attributes如果我们不喜欢property默认的命名方式,我们可以通过The getter= and setter= Attributes 来改变存取器方法名。最常用的就是对Boolean属性使用这个。可以把getter把惯例的改成is,例如:property

5、(getter=isRunning) BOOL running;现在生成存储器叫做isRunning和setRunning.而标注公共性质还是叫做running。下面是我们应该怎么用逗号使用它。Car *honda = Car alloc init; honda.running = YES; NSLog(%d,honda.running); NSLog(%d,honda isRunning);这些是唯一的属性,他们都是boolean标记。2、readonly属性readonly属性是一个很方便的方法让你的属性只读。这样会省略setter方法,并且防止作恶通过.调用,但是getter不受影响。例

6、如,我们修改running的属性为readonly,注:我们可以制定多个属性,然后用“,”分开:#import interface Car : NSObject property(getter=isRunning,readonly) BOOL running; -(void)startEngine;-(void)stopEngine;end不是让其他object改变running的属性,我们将会设置两个方法去访问。这两个方法的而实现如下:-(void)startEngine _running = YES;-(void)stopEngine _running = NO;要记得,property还

7、为我们生成了一个实例变量,这就是我们为什么可以访问_running在没有声明的条件下(我们也可以直接使用self.running因为这个属性是只读的)。让我们来运行下列代码测试:Car *honda = Car alloc init;/ honda.running = YES; NSLog(%d,honda.running); honda.running = NO;我们会发现最后一句出错,因为它是只读属性,无法修改。到这个地方,我们可以很方便快捷地让我们避免书写样板的getter和setter方法。而对remaining属性,这不是一个好的情况。他们也只适用于属性存储OC对象(相当于C数据类型

8、)。3、nonatomic属性原子性(Atomicity)的作用是属性在线程的环境中怎么行为。当你不仅仅有一个线程, 那么getter和setter可能会在同一时间去调用,这就意味着getter/setter可能会被另一个方法打扰,很有可能造成数据错误。原子的属性会封锁object,防止这种情况发生,确保get或者set操作的操作对象是完整的。没有被损坏。然而,这仅仅是一个线程安全的方面,我们必须要理解这一点。使用原子性并不能确保我们的代码就是线程安全的。属性用property声明默认是原子性的,这会导致一些花销,因此,如果你不是处在多线程环境(或者你正实现你自己的线程安全),你会用notat

9、omic属性重写这个行为,就像下边:property (nonatomic) NSString *model; /设置非原子性当使用原子性属性时,会有一个小的而且比较实际的警告。针对原子属性的属性访问器必须要么是生成的,要么是用户自定义的,只有传统非原子性的属性会让你混合搭配合成存储方法。你可以看一下,如果移去nonatomic从上边的代码,然后再Car.m添加传统的getter。会产生一个警告:Setter和getter必须被合成,或者用户自定义,或者属性必须是nonatomic4、内存管理在面向对象语言中,objects存在于计算机内存中,尤其在移动设备中,内存这是一个很缺乏的资源。内存管

10、理系统以一个高效的管理方式创建和破坏object,目标就是确保程序不占用超出它所需要的空间。许多语言都是通过垃圾回收去完成的,但是OC用的是一个更加高效替代品,就是Object ownership(目标拥有者)。当你开始与对象交互时,你会告诉对象自己,这就意味着它确保只要你再使用对象,它就会存在.当你不再使用的时候,你放弃所有权,如果对象没有其他的所有者,操作系统会销毁这个对象,然后释放底层内存资源。随着自动引用计数(ARC)出现,编译器自动管理你所有的对象,大多数情况下,意味着你从来不必担心内存管理系统是怎么工作的,但是,你必须明白strong,weak和copy属性,因为他们告诉编译器对象

11、应该有什么关系。5、Strong属性无论对象被指定为什么属性,强壮的属性可以创建拥有关系,这对所有对象属性来说是一种内隐行为,它默认是安全的,因为只要它被指定为strong属性,它就会却倒对对象的值存在。通过下面的例子,让我们看一下它是怎么工作的。interface Person : NSObject property(nonatomic)NSString *name;end它的实现如下,它property产生的使用默认的存储方法,它也重写了NSObject的描述方法,返回一个代表该对象的字符串。#import Person.himplementation Person-(NSString *

12、)description return self.name;end然后,让我们添加Person属性给车,改变Car.h如下:#import #import Person.hinterface Car : NSObjectproperty (nonatomic) NSString *model;property(nonatomic,strong) Person *driver;end然后考虑下边的代码:Person *john = Person alloc init;john.name = John;Car *honda = Car alloc init;honda.model = Honda

13、Civic;honda.driver = john;NSLog(% is driving the %,honda.driver,honda.model);只要driver是一个strong关联,honda对象就会持有john,这确保只要honda需要它,它就会有效。6、weak属性大多数情况下,强属性可以直观知道你想要什么对象属性,强引用会暴漏一个问题,例如,我们需要从driver引用他正在开的Car对象, 首先,我们需要给Person添加一个car属性:Person.h#import class Car;interface Person : NSObjectproperty(nonatomi

14、c)NSString *name;property(nonatomic,strong)Car *car;endclass Car 是对Car类的前声明,就像它告诉编译器,“相信我,Car类是存在的,所有不要想着去立刻找到它”。我们不用#import这样做,因为Car也导入了Person.h,那样我们会陷入无尽的导入循环(编译器不喜欢无穷的循环)。然后,添加下面的代码,在honda、dirvier分配后:Person *john = Person alloc init; john.name = John; Car *honda = Car alloc init; honda.model = Honda Civic; honda.driver = john; john.car = honda; /添加这行 NSLog(% is driving the %,honda.driver,honda.model);这样我们现在有一个现象,就是john拥有honda,honda拥有john。这就意味着他们相互拥有,所以尽管他们不再有用,内存管理系统也不能够释放他们。这叫做retain cycle(保持循环),是一种内存泄露的形式,内存泄露是很不

展开阅读全文
相关资源
相关搜索

当前位置:首页 > 办公文档 > 其它办公文档

电脑版 |金锄头文库版权所有
经营许可证:蜀ICP备13022795号 | 川公网安备 51140202000112号