iOS 深拷贝、浅拷贝(1)非容器类对象实例
来源:互联网 发布:西安市爱知中学官网 编辑:程序博客网 时间:2024/06/01 10:09
对象的复制就是复制一个对象作为副本,它会开辟一块新的内存(退内存)来存储副本对象,即源对象和副本对象是两块不同的内存区域,对象要具备复制功能,必须实现<NSCopying>协议或者<NSMutableCopying>协议,常用的可复制对象有:NSNumber、NSString、NSMutableString、NSArray、NSMutableArray、NSDictionary、NSMutableDictionary。自定义的对象要具有可复制性也要实现<NSCopying>协议或者<NSMutableCopying>协议,并实现该协议的 copyWithZone:方法活mutableCopyWithZone:方法。
copy方法:产生对象的副本是不可变的。
mutableCopy方法:产生对象的副本是可变的。
举个例子:
NSString *str = @"哈哈"; // 没有产生新对象 NSString *copyStr = [str copy]; // 产生新对象 NSMutableString *mutableCopyStr = [str mutableCopy]; NSLog(@"\n str = %p\n copyStr = %p\n mutableCopyStr = %p", str, copyStr, mutableCopyStr); NSMutableString *string = [NSMutableString stringWithString:@"呵呵"]; // 产生新对象 NSString *copyString = [string copy]; // 产生新对象 NSMutableString *mutableCopyString = [string mutableCopy]; NSLog(@"\n string = %p\n copyString = %p\n mutableCopyString = %p", string, copyString, mutableCopyString);
结果如下:
可以发现 只有在一种情况下才不会产生新对象地址。
什么是浅拷贝,什么是深拷贝?
浅拷贝:浅拷贝只复制对象本身,对象里的属性、包含的对象不做复制。属于指针拷贝,使原对象的引用计数+1,可以理解为创建了一个指向原对象的新指针而已,并没有创建一个全新的对象,不会产生新对象地址。
深拷贝:既复制对象本身,对象的属性也会复制一份。属于内容拷贝,会产生内存地址完全不一样的新的对象,创建后和原对象没有任何关系。
举个例子:
新建一个Person类。实现<NSCopying>协议,实现copyWithZone:方法。
@interface Person : NSObject<NSCopying>@property (nonatomic, assign) NSInteger age;@property (nonatomic, assign) NSInteger height;@property (nonatomic, strong) NSString *name;@end
@implementation Person-(id)copyWithZone:(NSZone *)zone{ Person *p = [[Person allocWithZone:zone] init]; return p;}@end
实例化该类,并copy对象:
Person *p = [[Person alloc] init]; p.age = 18; p.height = 175; p.name = @"abc"; Person *copyP = [p copy]; NSLog(@"\n p = %p\n copyP =%p",p,copyP); NSLog(@"\n name = %@\n age = %ld\n height = %ld",copyP.name,copyP.age,copyP.height);运行结果:
虽然copy了份新的对象,然而age,height,name值并未copy。那么咱们在在copyWithZone:方法中,对属性进行赋值即可:
-(id)copyWithZone:(NSZone *)zone{ Person *p = [[Person allocWithZone:zone] init]; p.age = self.age; p.height = self.height; p.name = self.name; return p;}
再运行,得到结果:
再说说property里的copy、strong,改一点代码:
NSMutableString *name = [NSMutableString stringWithFormat:@"abc"]; Person *p = [[Person alloc] init]; p.age = 18; p.height = 175;// p.name = @"abc"; p.name = name; Person *copyP = [p copy]; [name appendString: @"123"]; NSLog(@"\n name = %@\n age = %ld\n height = %ld",copyP.name,copyP.age,copyP.height);运行结果如果:
如果将name的修饰词用copy代替strong之后运行打印出来的p.name是abc,就不贴运行图了。name appendString:未能改变name的值,因为其内部copy新的对象,property copy 实际上就对name干了这个:
- (void)setName:(NSString *)name{ _name = [name copy];}
而这里传入的name刚好是NSMutableString,所以产生了新的对象地址,所以再改变原name的值并不能影响Person中的name。
以上是对非容器类对象的举例。
- iOS 深拷贝、浅拷贝(1)非容器类对象实例
- iOS 深拷贝、浅拷贝(2)容器类对象实例
- iOS-深拷贝浅拷贝实例
- 【iOS】自定义对象深拷贝、浅拷贝
- IOS详解深拷贝和浅拷贝的概念、具体的使用以及对于容器类(NSArray,NSDictionary 等)和非容器类(NSString,NSdata 等)拷贝的差异
- iOS 学习(深拷贝 浅拷贝)
- iOS伪拷贝, 浅拷贝, 深拷贝
- iOS 关于容器类的浅、深拷贝探究
- [ios]深拷贝,浅拷贝
- iOS深拷贝浅拷贝
- iOS学习笔记--浅拷贝和深拷贝——拷贝集合类(Copying Collections)
- object c的浅拷贝(地址拷贝)和深拷贝(对象拷贝)
- ios深拷贝,浅拷贝,拷贝自定义对象的简单介绍
- ios深拷贝,浅拷贝,拷贝自定义对象的简单介绍
- ios深拷贝,浅拷贝,拷贝自定义对象的简单介绍
- ios深拷贝,浅拷贝,拷贝自定义对象的简单介绍
- ios深拷贝,浅拷贝,拷贝自定义对象的简单介绍
- ios深拷贝,浅拷贝,拷贝自定义对象的简单介绍
- X Chen笔记---Centos下无法上网,启动网卡时bring up interface报错
- API26下gradle.build加载recycleview同步时报错
- springboot学习笔记(五) JPA
- 贪心:迪杰斯特拉算法
- drop、truncate和delete的区别
- iOS 深拷贝、浅拷贝(1)非容器类对象实例
- JavaScript 检测视频和音频的格式
- Android 静态代码检查实践
- Spring学习笔记(八) --- 面向切面的Spring
- springboot学习笔记(六) Mybatis
- activiti explorer工作流创建及使用
- python里使用正则表达式的全匹配功能
- HDU 1028 Ignatius and the Princess III(递推)
- 10月第三周