一、深拷贝和浅拷贝
浅拷贝:只创建一个新的指针,指向原指针指向的内存
深拷贝:创建一个新的指针,并开辟新的内存空间,内容拷贝自原指针指向的内存,并指向它
假设我们要对一个不可变的对象进行不可变copy(原来的对象不可变,新对象也不可变)。就没必要给新对象新建一块内存,反正大家都不可以对这个对象进行改变,那都使用一个就可以。所以iOS系统规定浅拷贝引用计数器加1就行。而需要给新对象开闭内存空间的,就是深拷贝。
copy得到的类型一定是不可变的 mutableCopy得到的类型一定是可变的 使用mutable,都是深拷贝(不管是拷贝类型还是拷贝方法);但是copy也有深拷贝;
浅拷贝即指针拷贝,可以认为是给一只狗加了一条绳子;深拷贝不但拷贝了对象的指针,还在系统中在分配了一块内存用来存放拷贝对象的内容,可以认为是产生了一条带绳子的新狗。即浅拷贝是两根绳子一条狗,深拷贝是两根绳子两条狗且每只狗对应各自的绳子。
1.浅拷贝
int main(int argc, const char * argv[]) {
@autoreleasepool {
NSString* str = @"Objective-C";
NSString* str2 = [str copy];
NSLog(@"str = %@, str2 = %@", str, str2);
}
return 0;
}
NSArray* arr1 = [NSArray arrayWithObjects:@"苹果", @"桃子", @"葡萄", nil];
用mutbaleCopy复制一个不同类型的NSMutableArray数组
NSMutableArray* arr2 = [arr1 mutableCopy];
打印两者的指针地址,不同
NSLog(@"arr1 = %p, arr2 = %p", arr1, arr2);
NSLog(@"======打印arr1中的元素======");
for (id object in arr1) {
NSLog(@"%@", object);
}
NSLog(@"======打印arr2中的元素======");
for (id object in arr2) {
NSLog(@"%@", object);
}
总结:创建出了一个新的对象,指针地址自然就不同,但副本中的元素都和被复制的对象中的元素相同,所以它是一个深复制
二、copy基本概念
1.什么是copy
特点:
修改原文件的内容
修改副本文件的内容,不会影响源文件
OC中的copy
作用: 利用一个源对象产生一个副本对象
特点:
修改源对象的属性和行为,不会影响副本对象
修改副本对象的属性和行为,不会影响源对象
2.copy与mutableCopy
一个对象可以调用copy
或mutableCopy
方法来创建一个副本对象
copy
:创建的是不可变副本(如NSString、NSArray、NSDictionary)
mutableCopy
:创建的是可变副本(NSMutableString、NSMutableDictionary
)
使用copy功能的前提
copy
:需要遵守NSCopying
协议,实现copyWithZone:
方法
@protocol NSCopying
- (id)copyWithZone:(NSZone*)zone;
@end
使用mutableCopy功能的前提
需要遵守NSMutableCopying
协议,实现mutableCopyWithZone:
方法
@protocol NSmutableCopying
- (id)mutableCopyWithZone:(NSZone*)zone;
@end
int main(int argc, const char * argv[]) {
@autoreleasepool {
NSString* str = @"Objective-C";
NSMutableString* str2 = [str mutableCopy];
NSLog(@"str = %@, str2 = %@", str, str2);
}
return 0;
}
分析:
上面代码中使用mutableCopy对str进行复制,所产生的新的对象副本类型是NSMutableString类型的,所以要新创建一个NSMutableString类型的str2,将刚才产生的副本存入
1.如果是通过不可变对象调用了
copy
方法,那么不会生成一个新的对象原因:因为原来的对象是不能修改的,拷贝出来的对象也是不能修改的,既然两个都不能修改,所以永远不能影响到另外一个对象,那么已经符合需求(OC为了对内存进行优化,就不会生成一个新的对象)
2.OC中有部分对象已经遵守了NSCopy
和NSMutableCopy
这两个协议,如NSString
。但如果是自定义的对象,如自定义一个person*
对象,并不遵守这两个协议。
原文地址:https://blog.csdn.net/weixin_61558111/article/details/125246723
本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。
如若转载,请注明出处:http://www.7code.cn/show_11435.html
如若内容造成侵权/违法违规/事实不符,请联系代码007邮箱:suwngjj01@126.com进行投诉反馈,一经查实,立即删除!