三、@property修饰符与属性关键字

一、@property

1. @synthesize 与 @dynamic
在声明@property 属性后,会有两种实现选择@synthesize 和 @dynamic

2. 两者区别

  • @synthesize ,表示在编译阶段 编译器会自动生成 setter/getter方法的实现;
  • @dynamic,表示通知编译器不自动生成,由用户手动添加属性的 setter/getter方法;

3. @property重写setter方法
如果使用@property生成的属性,重写setter方法会报错。
原因: 重写setter方法,那@property就不会再自动生成setter和getter方法,也不会生成带下划线的成员变量,自然无法访问报找不到该对象。
解决: 使用 @synthesize

   @synthesize object = _object;

二、属性关键字

1. 默认属性关键字
默认包含: atomic、 readwrite、assign(基本数据类型)、strong(对象);

2. 关键字分类

  • 读写权限: readonly、readwrite ;
  • 原子性: atomic、noatomic ;
  • 内存管理: assign, weak, unsafe_unretained, copy, strong,retain;
    注意点
    retain用在MRC,当retain作为@property属性关键字时:
    @property(nonatomic, retain) 相当于系统自动帮我们处理了属性的setter方法,如下
 -(void)setObject:(id)Obj
 {
   if(obj != obj) {    // 防止重复赋值,指针指向被释放的对象造成崩溃
   [_obj release];     // 防止前一个对象没被释放,造成的内存泄漏
   [obj retain];       // 多对象引用,保证A存在B存在,A释放B随后释放
   _obj = obj;
  }
}

同时注意,在MRC下retain作为关键字,dealloc中都需要把属性进行释放。才能防止内存泄漏。

 -(void)dealloc
 {
  [_obj release];  // ...
  [super dealloc];
}

三、常见比较

1. 原子性 atomic 与 nonatomic区别?
  • atomic 是系统默认的属性,给getter/setter方法会进行加锁,在一定程度保证线程安全;
  • nonatomic 没有加锁,不能保证线程安全, 但是访问更快;
  • 设置属性一般会使用 nonatomic , 虽然atomic能保证线程安全但是保护范围仅仅是getter/setter方法,而且耗费资源、访问更慢。
2. assign 和 weak 的区别?
  • assign 可以修饰基本数据类型, weak用来修饰对象;
  • assign 修饰的对象被释放后,对象对应的指针没有置为 nil 从而造成野指针;
    weak 修饰的对象被释放后,对象指针置为 nil 。
3. copy 和 strong 的区别?
  • copy分为浅拷贝和深拷贝;
    浅拷贝不会开辟新的地址产生新的对象,两个指针指向同一块地址,因此引用计数+1;
    深拷贝会开辟新的地址产生新的对象,两个指针各自指向不同的地址,因此引用计数不会+1;
  • copy 和 strong的区别
    strong 强引用对象,操作仍是浅拷贝; copy修饰的对象,分深浅拷贝两种;引用计数也有不同;
4. 为什么代理使用 weak 修饰?

答:防止循环引用

  • 如以UITableView为例, tableView作为控制器vc的属性, vc 强引用tableView;
    tableView需要设置vc为代理,self.delegate = vc; 如果代理也是强引用则会造成循环引用。 因此代理使用weak;
5. 为什么 block 使用copy修饰?

答: Block作为OC对象, 包含 全局Block、 堆Block、栈Block 三种;
在Block没有访问外部变量时,一般是放在全局区;当需要访问外部变量时,分MRC和ARC两种;

  • MRC下,Block是放在栈中的,会随着作用域的结束被系统收回,当外部变量调用空的对象就会造成崩溃;
    因此使用copy,复制一份在堆内存中,始终强引用防止被销毁;
  • ARC下,系统自动的对block进行了copy,因此ARC下的Block放在堆中;
6. 为什么 NSString 使用copy修饰?

答:

7. 使用copy修饰可变数组 (NSMutableArray) 会造成的问题?

答:copy修饰可变数组NSMutableArray,深拷贝,最终会变成不可变数组NSArray。
那么原来可变数组具备的添加、删除对象的方法,都不可用。 此时生成的不可变数组再使用上述方法就会崩溃。

8. 为什么xib或storyBoard拖线的控件使用weak,而代码创建的使用strong?
  • IBOutlet使用weak的原因
    (1) 拖线产生的对象会添加到控制器的view的subViews里,
    控制器vc 对其view肯定是强引用,view持有控件但是控制器不需要直接持有。如果控件也设置strong,存在父控件被销毁子控件仍然存在从而内存泄漏; 并且为了保证父子控件相同的生命周期,也应该使用weak;
  • 代码使用strong 的原因
    代码定义的控件如button,在使用是 self.button 即控制器直接持有button, 强引用因此使用strong 。
9. __weak 与__block

weak 是修饰属性, 而 __weak 和 __block 用于修饰变量。

  • 使用场景不同
    __weak 用于断开 block 容易产生的循环引用;
    __ block 则是由于内部想要修改外部的值,由原来的值传递转换成指针传递。
  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

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

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

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值