Objective C:何时使用 NSCopying 以及何时使用 @属性(copy)?
Objective C: When to use NSCopying and and to use @property(copy)?
根据 Apple 文档:
NS复制
复制对象会创建一个与原始对象具有相同 class 和属性的新对象。当您想要对象包含的数据的您自己的版本时,您可以复制该对象。
https://developer.apple.com/library/ios/documentation/General/Conceptual/DevPedia-CocoaCore/ObjectCopying.html
@属性(copy) 使用copy自动向新分配的对象发送一个-copy消息(这将创建一个副本传递的对象并将该副本分配给 属性 而不是 。https://developer.apple.com/library/ios/documentation/General/Conceptual/DevPedia-CocoaCore/ObjectCopying.html
我知道已经有很多关于这些概念的单独内容。
但是有人可以解释以下场景:
这两个可以互换使用
这两个需要一起使用才能实现一些东西。(因为如果我们创建一个自定义class如果我们创建这样一个[=的对象,系统将如何直接创建一个副本42=] 与 @属性(复制))?
当你使用@属性(copy)id xxx;确切的代码将是这样的:
-(id)xxx {
return [_xxx copy];
}
NSCopying
是一个协议,表示class可以被复制。您需要实施 class 的复制方法才能使其正常工作。
我认为您误解了 copy
属性。它始终使用 NSCopying
行为。 NSCopying
定义了一个 copy
方法来从现有实例创建新实例,并且 copy
属性 使用此方法保存数据,而不是保留原始实例。
要了解 copy
属性 的必要性,首先我们必须了解可变对象和不可变对象之间的区别。例如,让我们看一下 NSMutableArray
和 NSArray
。前者是可变的,后者是不可变的。当我们在某处传递 NSMutableArray
并保留它时,我们希望避免其他 类 改变我们的内部状态,这就是为什么我们要复制数组的当前值而不是保存原始可变数组。
例如:
@interface A : NSObject
@property (nonatomic, strong) NSArray *array1;
@property (nonatomic, copy) NSArray *array2;
@end
NSMutableArray *array = [NSMutableArray array];
[array addObject:@"a"];
[array addObject:@"b"];
[array addObject:@"c"];
A *a = [[A alloc] init];
a.array1 = array;
a.array2 = array;
// now we have changed the contents of a.array1 but a.array2 stays the same!
[array addObject:@"d"];
有趣的是,不可变对象不会 return 来自 copy
的新实例,它们 return self
因为如果一个对象是不可变的,它确实没关系。
根据 Apple 文档:
NS复制 复制对象会创建一个与原始对象具有相同 class 和属性的新对象。当您想要对象包含的数据的您自己的版本时,您可以复制该对象。 https://developer.apple.com/library/ios/documentation/General/Conceptual/DevPedia-CocoaCore/ObjectCopying.html
@属性(copy) 使用copy自动向新分配的对象发送一个-copy消息(这将创建一个副本传递的对象并将该副本分配给 属性 而不是 。https://developer.apple.com/library/ios/documentation/General/Conceptual/DevPedia-CocoaCore/ObjectCopying.html
我知道已经有很多关于这些概念的单独内容。
但是有人可以解释以下场景:
这两个可以互换使用
这两个需要一起使用才能实现一些东西。(因为如果我们创建一个自定义class如果我们创建这样一个[=的对象,系统将如何直接创建一个副本42=] 与 @属性(复制))?
当你使用@属性(copy)id xxx;确切的代码将是这样的:
-(id)xxx {
return [_xxx copy];
}
NSCopying
是一个协议,表示class可以被复制。您需要实施 class 的复制方法才能使其正常工作。
我认为您误解了 copy
属性。它始终使用 NSCopying
行为。 NSCopying
定义了一个 copy
方法来从现有实例创建新实例,并且 copy
属性 使用此方法保存数据,而不是保留原始实例。
要了解 copy
属性 的必要性,首先我们必须了解可变对象和不可变对象之间的区别。例如,让我们看一下 NSMutableArray
和 NSArray
。前者是可变的,后者是不可变的。当我们在某处传递 NSMutableArray
并保留它时,我们希望避免其他 类 改变我们的内部状态,这就是为什么我们要复制数组的当前值而不是保存原始可变数组。
例如:
@interface A : NSObject
@property (nonatomic, strong) NSArray *array1;
@property (nonatomic, copy) NSArray *array2;
@end
NSMutableArray *array = [NSMutableArray array];
[array addObject:@"a"];
[array addObject:@"b"];
[array addObject:@"c"];
A *a = [[A alloc] init];
a.array1 = array;
a.array2 = array;
// now we have changed the contents of a.array1 but a.array2 stays the same!
[array addObject:@"d"];
有趣的是,不可变对象不会 return 来自 copy
的新实例,它们 return self
因为如果一个对象是不可变的,它确实没关系。