浅复制:将原始对象的指针值复制到副本中,即指针复制,原始对象和副本共享引用的数据,相当于创建了一个文件的快捷方式。
深复制:复制原始对象指针所引用的数据,并将其赋给副本对象,即内容复制,相当于创建了一份新的文件。
可变对象复制与不可变对象复制
在Foundation框架中,常用的几个类,如NSString、NSArray以及NSDictionary都有其对应的可变子类。当对不同类的对象进行复制时,系统会采用不同的复制方式,有的采用浅复制,有的采用深复制。
在NSObject类中提供了两种复制的实例方法,copy和mutableCopy。当对象调用copy方法时,会返回NSCopying协议中的copyWithZone:方法的返回结果,前提是对象在定义中遵守了NSCopying协议。
-(id)copy;
当对象调用mutableCopy方法时,会返回NSCopying协议中mutableCopyWithZone:方法的返回结果,前提是对象在定义中遵守了NSCopying协议。
-(id)mutableCopy;
当对不同类型的对象分别使用copy和mutableCopy方法进行复制时,可能对应不同的复制类型(深复制或浅复制),这取决于类中copyWithZone:以及mutableCopyWithZone:方法的实现逻辑。
//
在Foundation框架中,可变类/不可变类与容器类/非容器类进行分类组合就构成了四种情况:容器类不可变对象,容器类可变对象,非容器类不可变对象以及非容器类可变对象。这四种组合进行复制时,得到的复制对象会有所区别。
1、NSString对象的复制属于非容器类不可变对象的复制。通过验证,可以得到如下结论:NSString类使用copy为浅复制(指针复制),使用mutableCopy为深复制。
2、NSMutableString对象的复制属于非容器类且可变对象的复制。通过验证,可以得到如下结论:NSMutableString类使用copy或者mutableCopy均为深复制。
3、NSArray对象的复制属于容器类且不可变对象的复制,通过验证,可以得到如下结论:NSArray类使用copy为浅复制,使用mutableCopy为深复制,另外,不论使用copy还是mutableCopy,容器内的对象都是浅复制。
4、NSMutableArray对象复制属于容器类且可变对象的复制,通过验证,可以得到如下结论:NSMutableArray类不论使用copy还是mutableCopy都为深复制,容器内的对象都是浅复制。
5、NSDictionary对象的复制属于容器类且不可变对象的复制,通过验证,可以得到如下结论:NSDictionary类使用copy为浅复制,使用mutableCopy为深复制,容器内的对象都是浅复制。
6、NSMutableDictionary对象复制属于容器类且可变对象的复制,通过验证,可以得到如下结论:NSMutableDictionary类不论使用copy还是mutableCopy均为深复制,容器内的对象都是浅复制。
自定义复制:对于自定义对象的复制,首先要保证在类的定义中遵守NSCopying协议,然后实现copyWithZone:方法,对于自定义对象的复制特性(浅复制或深复制),都取决于copyWithZone:方法中的实现情况,对于类中定义的属性也需要综合考虑其定义中有关内存管理的特性(strong/weak/copy/assign)。