在子类的子类中实现NSCopying [英] Implementing NSCopying in Subclass of Subclass
问题描述
我有一个很小的类层次结构,在实现copyWithZone:
时遇到了麻烦.我已经阅读了NSCopying文档,但找不到正确的答案.
I have a small class hierarchy that I'm having trouble implementing copyWithZone:
for. I've read the NSCopying documentation, and I can't find the correct answer.
参加两个课程:形状和正方形.正方形定义为:
Take two classes: Shape and Square. Square is defined as:
@interface Square : Shape
没有惊喜.每个类具有 one 属性,Shape具有"sides"整数,Square具有"width"整数. copyWithZone:
方法如下所示:
No surprise there. Each class has one property, Shape has a "sides" int, and Square has a "width" int. The copyWithZone:
methods are seen below:
形状
- (id)copyWithZone:(NSZone *)zone {
Shape *s = [[Shape alloc] init];
s.sides = self.sides;
return s;
}
平方
- (id)copyWithZone:(NSZone *)zone {
Square *s = (Square *)[super copyWithZone:zone];
s.width = self.width;
return s;
}
看看文档,这似乎是做事的正确"方法.
Looking at the documentation, this seems to be the "right" way to do things.
不是.
如果您尝试设置/访问由copyWithZone:
方法返回的Square的width属性,则它将失败,并显示类似以下错误:
If you were to try to set/access the width property of a Square returned by the copyWithZone:
method, it would fail with an error similar to the one below:
2010-12-17 11:55:35.441 Hierarchy[22617:a0f] *** Terminating app due to uncaught exception 'NSInvalidArgumentException', reason: '-[Shape setWidth:]: unrecognized selector sent to instance 0x10010c970'
在Square方法中调用[super copyWithZone:zone];
实际上会返回一个Shape.您甚至可以在该方法中设置width属性,这是一个奇迹.
Calling [super copyWithZone:zone];
in the Square method actually returns a Shape. It's a miracle you're even allowed to set the width property in that method.
话虽这么说,如何以一种对子类实施NSCopying 的方式,使不让它们负责复制其超类的变量?
That having been said, how does one implement NSCopying for subclasses in a way that does not make them responsible for copying the variables of its superclass?
推荐答案
在问完之后您马上意识到的事情之一.
One of those things you realize right after asking...
超类( Shape )中copyWithZone:
的实现不应假定它是Shape.因此,不是我上面提到的错误方法:
The implementation of copyWithZone:
in the superclass (Shape) shouldn't be assuming it's a Shape. So instead of the wrong way, as I mentioned above:
- (id)copyWithZone:(NSZone *)zone {
Shape *s = [[Shape allocWithZone:zone] init];
s.sides = self.sides;
return s;
}
您应该改用:
- (id)copyWithZone:(NSZone *)zone {
Shape *s = [[[self class] allocWithZone:zone] init]; // <-- NOTE CHANGE
s.sides = self.sides;
return s;
}
这篇关于在子类的子类中实现NSCopying的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!