面试题答案
一键面试潜在问题
- 内存管理:
- ARC环境:扩展中定义的隐藏属性在ARC下,系统会自动管理其内存。但若属性是对象类型,可能因循环引用导致对象无法释放。比如,A类扩展中有个属性指向B类对象,而B类对象又反向持有A类对象,就会造成循环引用。
- MRC环境:开发者需手动管理隐藏属性的内存。若忘记在合适时机调用
release
方法,会导致内存泄漏。例如在对象销毁时未释放属性所指向的对象。
- 安全性:
- 隐藏方法被恶意调用风险:由于Objective - C是动态语言,通过运行时机制,隐藏方法可被外部类获取并调用。恶意调用可能导致程序逻辑混乱、数据错误或安全漏洞。比如,隐藏的敏感数据操作方法被非法调用,篡改重要数据。
解决方案
- 内存管理:
- ARC环境:使用弱引用(
weak
)或无主引用(unowned
)打破循环引用。例如在上述A类和B类的循环引用场景中,将其中一个引用设置为weak
或unowned
。如果A类中属性指向B类对象,可将该属性定义为weak
,即@property (nonatomic, weak) BClass *bObject;
。 - MRC环境:在对象的
dealloc
方法中,确保手动释放隐藏属性所指向的对象。比如[myHiddenProperty release];
,同时在属性赋值时使用retain
来增加引用计数,如[self setMyHiddenProperty:[[SomeObject alloc] init]];
- ARC环境:使用弱引用(
- 安全性:
- 权限控制:可通过访问修饰符限制方法访问。对于Objective - C,虽然没有像其他语言那样严格的访问修饰符,但可通过将敏感方法放在只在类内部使用的分类中,不在公共头文件中暴露。例如将敏感方法放在
@interface MyClass (Private)
分类中,不在.h
文件中声明。 - 运行时检查:在隐藏方法内部添加运行时检查逻辑。比如检查调用者是否是预期的类或对象,可通过
[self class]
获取当前类,与预期类进行比较。若不匹配,直接返回或抛出异常。示例代码如下:
- 权限控制:可通过访问修饰符限制方法访问。对于Objective - C,虽然没有像其他语言那样严格的访问修饰符,但可通过将敏感方法放在只在类内部使用的分类中,不在公共头文件中暴露。例如将敏感方法放在
- (void)hiddenMethod {
if (![[self class] isEqual:[ExpectedClass class]]) {
// 返回或抛出异常
return;
}
// 正常方法逻辑
}