@interface ViewController ()
// Strong
@property (nonatomic, strong) NSString *sString;
@property (nonatomic, strong) NSArray *sArray;
// Copy
@property (nonatomic, copy) NSString *cString;
@property (nonatomic, copy) NSArray *cArray;
@end
@implementation ViewController
- (void)viewDidLoad {
[super viewDidLoad];
// 使用strong时,如果这个属性指向一个可变对象,修改可变对象时,这个属性值也会被修改
NSMutableString *mString = [NSMutableString stringWithString:@"strong"];
self.sString = mString;
self.cString = mString;
[mString appendString:@"_change"];
NSLog(@"\n sString = %@ \n cString = %@", self.sString, self.cString);
// NString,NSArray,NSDictionary都有自己对应的子类:NSMutableString,NSMutableArray,NSMutableDictionary,而父类指针可以指向子类对象,使用copy可以让本对象不受外界(子对象)影响,无论给我传入的是一个可变对象还是一个不可变对象,都能保证自身持有的是一个不可变副本
NSMutableArray *mArray = [NSMutableArray arrayWithObjects:@1, @2, @3, nil];
self.sArray = mArray;
self.cArray = mArray;
[mArray addObject:@4];
NSLog(@"\n sArray = %@ \n cArray = %@", self.sArray, self.cArray);
}
@end
日志输出
使用copy能保证属性不被子类对象修改时同时被修改。
sString = strong_change
cString = strong
sArray = (
1,
2,
3,
4
)
cArray = (
1,
2,
3
)
Copy 和 MutableCopy
// 浅拷贝:地址的拷贝
// 深拷贝:内容的拷贝
// 非集合对象的copy
NSString *string = @"string";
NSString *stringCopy = [string copy];
NSString *stringMCopy = [string mutableCopy];
NSLog(@"\nstring: \n%p \nstringCopy: \n%p \nstringMCopy: \n%p", string, stringCopy, stringMCopy);
string:
0x100270088
stringCopy:
0x100270088
stringMCopy:
0x1c425a490
// 非集合对象的mutableCopy
NSMutableString *mString = [NSMutableString stringWithString:@"mString"];
NSString *mStringCopy = [mString copy];
NSString *mStringMCopy = [mString mutableCopy];
NSLog(@"\nmString: \n%p \nmStringCopy: \n%p \nmStringMCopy: \n%p", mString, mStringCopy, mStringMCopy);
mString:
0x1c425a2e0
mStringCopy:
0xa676e697274536d7
mStringMCopy:
0x1c425a070
// 集合对象的copy NSArray,NSDictionary,NSSet
NSArray *array = @[@1, @2, @3];
NSArray *arrayCopy = [array copy];
NSMutableArray *arrayMCopy = [array mutableCopy];
NSLog(@"\narray: \n%p \narrayCopy: \n%p \narrayMCopy: \n%p", array, arrayCopy, arrayMCopy);
array:
0x1c425a580
arrayCopy:
0x1c425a580
arrayMCopy:
0x1c425a0a0
// 集合对象的mutableCopy
NSMutableArray *mArray = [NSMutableArray arrayWithObjects:@1, @2, @3, nil];
NSArray *mArrayCopy = [mArray copy];
NSMutableArray *mArrayMCopy = [mArray mutableCopy];
NSLog(@"\nmArray: \n%p \nmArrayCopy: \n%p \nmArrayMCopy: \n%p", mArray, mArrayCopy, mArrayMCopy);
mArray:
0x1c425a640
mArrayCopy:
0x1c425a1f0
mArrayMCopy:
0x1c425a3d0
[immutableObject copy]是浅拷贝
[immutableObject mutableCopy]是深拷贝
[mutableObject copy]是深拷贝
[mutableObject mutableCopy]是深拷贝
集合对象的深拷贝只是对象本身,而集合对象的元素还是地址的拷贝,即单层深拷贝(浅拷贝)
block为什么要使用copy
block使用copy是在MRC中延续下来的,在MRC下,方法内部的block是存放在栈区,使用copy会将block拷贝到堆区。
在ARC下编译器会自动对block进行copy,因此我们使用copy或者strong的效果是一样的。但是我们在ARC下继续使用copy可以提醒我们编译器会自动帮我们实现copy的操作。
网友评论