Summary of copy in iOS

Introduction copy and mutableCopy introduce the benefits of deep copy and shallow copy block why use copy copy with respect to direct assignment

Preparatory knowledge:

Memory stack area: the compiler automatically assigned to release, the function of the stored parameter values, the value of local variables, etc.

Memory heap area: the general allocation of release by the programmer, if the programmer does not release, the program may be recovered by the end of OS. Note that it is different from the heap in the data structure, the allocation method is similar to the linked list

Copy method and mutableCopy method

If you want to create an object, the object and content of the source object, then you can consider the use of copy (copy or mutableCopy), first of all, I will use a string array, a dictionary of the three common objects to show the difference between copy and mutableCopy.


NSString @ *string = "Jerry"; 
[string copy] --> copy of content for the Jerry type NSString [string mutableCopy] -->
string; copy content string Jerry for type NSMutableString


NSDictionary *dict = "name" @{@: @ "Jerry"}; 
[dict copy] --> copy of content and the same type of Dict NSDictionary
[dict mutableCopy] --> dictionary; copy of content and dict of the same type NSMutableDictionary dictionary


NSArray *array @[@ = "Jerry"]; 
[array copy] --> copy of content and the same array NSArray type
[array mutableCopy] array --> copy the contents of the array with the same type of NSMutableArray array


Object type copy copy is immutable type (e.g., NSString, NSDictionary, NSArray and so on) object type mutableCopy copy is variable types (e.g., NSMutableString, NSMutableDictionary, NSMutableArray etc.)

Deep Copy and Shallow Copy

What is a deep copy, what is a shallow copy?

A deep copy of the source object: the object and copy the address out of the inconsistent! This means I modify the object copy value on the value of the source object without any influence.
shallow copy: the object and the source object address consistent copy out! This means I modify the copy object value will directly affect the source object.

It is necessary to correct some erroneous views on the Internet (see below)

Copy is a shallow copy, mutableCopy is a deep copy

We know that when we use copy to copy an immutable object from a mutable object, this is a deep copy rather than a shallow copy!!

Note that there is a difference between deep and shallow copy!!!

For the NSString object, it is a deep copy of a deep copy, a shallow copy is a shallow copy, without any objection. But for
NSArray, NSDictionary NSSet, the container class object? Of course is still a shallow copy of the pointer is copied, the deep copy means with the object container and container with copy or copy only the container? The object, object in the container is simply cited? There are two cases, I call it incomplete deep copy and deep copy completely

Incomplete deep copy

An incomplete deep copy is a copy of a container object, a copy of a shell, and only a reference to the object in the container

Summary of copy in iOS
incomplete deep copy.Png

So we know that even if we modify the copyArray will not affect the source array, but I modify the copyArray array by object, corresponding to the source array will also be modified in the object, we can test their own

Completely deep copy

A full copy is a copy of the object, including the inside of the container

Summary of copy in iOS
completely deep copy.Png

Through the picture can be very clear that, in this case, whether it is to modify the copyArray or modify the copyArray array by object, the source array will not cause any impact

PS: the default state refers to a deep copy of incomplete deep copy, such as to achieve complete deep copy, to override the copyWithZone: method to achieve complete deep copy needs. The general idea is as follows, in the copyWithZone: object assignment not assigned directly but through the copy method can be realized, where no specific discussion since. Asked the friend, then paste on the sample code.
Person.m / 
- (ID) copyWithZone: (NSZone *) zone

Person [[Person allocWithZone:zone] {*cpyPerson = init];
cpyPerson.age = self.age;
return cpyPerson;

NSArray} / /
- (ID) copy
NSArray [[NSArray alloc] {
*cpyArray = initWithArray:self copyItems:YES];
return cpyArray;

Person} / / *p1 = [[Person alloc] init];
Person *p2 = [[Person alloc] init];
NSArray *array = @[p1, p2];
NSArray *cpyArray = [array copy];
NSLog ("% @ @ -% @", array, cpyArray); wpap6 03001br / / output
< Person: 0x100204af0>
< Person:, 0x100206b20>
) - (
< Person: 0x100207910>
< Person:, 0x1002074d0>

This can be done completely deep copy purpose.
PS: the official documentation of the default inside the copy method calls the copyWithZone method, but the NSArray because of the unknown cause of the copy method does not call copyWithZone (probably because the concept of zone OC has been abandoned in Apple’s official documents have said), so here I would use the classification overrides the copy method of NSArray, apple is not recommended to do so.

Block why use copy?

First of all, block is a block object, so the theory is retain/release. But the block at the time of creation it is the default memory is allocated on the stack (stack), but not on the stack (heap). So its scope is limited to the current context when creating (function, method…), when you call the block in the overseas, the program will crash.

Summary of copy in iOS
Apple official documents

In general you don’t need to call copy or retain on your own, but only if you need to use the block definition domain outside of the copy. to move the block from the memory stack to the heap in the block. area

In fact, block copy is MRC to stay is a traditional, in MRC, such as the above, create the method in the block in the stack area, the use of copy can put him in the heap area, so in scope to call the block program will not collapse. But in ARC, copy and strong all the same, because the block retain is to use copy to achieve, so block can use copy loaded force, that he is coming from MRC.. hehe

Benefits of copy relative to direct valuation

Look at the following code:

Direct assignment of Summary of copy in iOS

Guess what the console output is (Kobe), (Kobe, McGrady)?
is wrong!!!

Array = (

McGragy), mArray = (

为什么??? 明明可变数组添加对象是在赋值之后, 为什么后面添加对象还会影响到不可变数组呢??
原因很简单, 因为Objective-C support polymorphism.
所以表面上self.array是NSArray对象, 其实骨子里是NSMutableArray对象.这样的话将会对后期DEBUG增加很大的成本, 可能会导致莫名其妙的错误.
再看以下代码 :

Summary of copy in iOS
using copy

Guess what the output will be?

Array = (
), mArray = (

这样就能保证不管赋值的是可变还是不可变数组, NSArray就是NSArray了!(你爸就是你爸, 不可能变成你了)

So now we know why @property in NSString, NSArray, NSDictionary attributes why most of the time with copy instead of strong reason?


Here to make a map to help the novice understand the difference between copy and mutableCopy, please ignore God ^_^

Summary of copy in iOS
copy and mutableCopy

If you can use copy correctly in your project, you will have no small help to the program!!

We welcome the attention of @Jerry4me, I will not concern rookie growth ^_^. updated learning experience and articles.