在以下示例中,可能会出现哪些问题。
id c = [Person alloc];
[c init];
您示例中代码的主要问题是,在某些情况下,-init 方法返回的对象与您使用 +alloc 创建的对象不同。如果发生这种情况,那么您的代码将不正确,因为您没有将结果分配[c init]
给 c,并且您最终会使用错误的对象(并且那个对象没有正确初始化)。这就是为什么标准的习惯用法总是将 +alloc 和 -init 组合在同一行:
id c = [[Person alloc] init];
现在,您可能已经编写了 Person 类,并且掌握了 -init 总是返回相同对象的第一手知识,但是我不必非常熟悉 Person 的内部工作原理来阅读您的代码并了解它是否是正确与否。从某种意义上说,如果您遵循通常的约定,任何人都可以说它正在做正确的事情,因此您的代码“更好”。
我认为将 c 声明为类型 id 并不可怕,但在这种情况下看起来确实很愚蠢。您知道c 将是 Person* 类型,那么为什么将其声明为 id 并丢弃编译器可以用来帮助您编写更好代码的有用信息呢?如果有充分的理由使用 id,那很好,但如果您可以更具体地了解您应该使用的类型。
使用id
泛型类型时,如果您尝试调用不存在的方法,您将不会收到警告。编译器假定您知道自己在做什么。
否则,没有我能想到的问题。在几种情况下很常见(想想异构容器类型的快速枚举)
另一个潜在的危险是,随着时间的推移,您可能会添加仅在某些情况下意外执行 init 的逻辑......留下一个已分配但从未初始化的对象意味着其中的所有值本质上都是随机的,并且它打算执行的任何设置代码都是尚未完成。
首先,类型转换问题。每次你想使用' c
',你可能需要(Person *)
,即类型转换它。
其次,如果您在 Person 中声明了任何方法,则不能将其称为[c aMthod]
样式,必须使用,[(Person *) c aMethod].