我正在研究 SKNode
的子类,名为 UtilityNode
@implementation UtilityNode
- (id)initWithName:(NSString *)rootName {
self = [super init];
if(self) {
[self setName:rootName]; // ?
}
return self;
}
@end
我正在为新节点 initWithName:
设置一个指定的初始化程序,在创建新子类时,我试图在其中初始化父类(super class) SKNode
的名称。我的印象是我可以只写 _name = rootName;
但 _name 被标记为未声明。我已经通过使用 [self setName:rootName];
使其正常工作(正如您在上面看到的那样);有谁能对此有所启发,我这样做是否正确?
最佳答案
这是正确的。 _name
实例变量可能被声明为 @private
(自动合成属性的默认值),因此子类无法访问它。
在精心设计的类层次结构中,特别是没有可用源代码的框架类中,您会发现大多数(如果不是全部)实例变量都无法被子类访问,因为它隐藏了实现细节并使得将来可能对基类进行更改。想象一下,如果基类需要在 name 属性更改时验证它 - 如果子类可以直接分配给 ivar,它们将绕过添加到 ivar setter 方法的检查。
PS:我发现点符号在眼睛上更友好:
self.name = rootName;
更新关于“不要在 init/dealloc 中向 self
发送消息”规则:
通过重新设计类以在其 init 方法中不采用非必要参数,可以轻松避免这种情况。这个子类的一个更简洁的版本是:
UtilityNode* un = [UtilityNode node];
un.name = @"some name";
如果节点绝对需要设置参数,则在要求名称有效的方法中通过 NSAssert
警告用户。
关于ios - 从子类设置父类(super class)的属性?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/22506966/