Objective-C返回类型:“ - (id)init”vs“ - (ClassName *)init”

时间:2014-08-22 20:42:22

标签: ios objective-c

我正在关注这个初学者教程http://www.raywenderlich.com/1797/ios-tutorial-how-to-create-a-simple-iphone-app-part-1,我对此类及其实现有疑问:

 RWTScaryBugData.h

 @interface RWTScaryBugData : NSObject

 @property (strong) NSString *title;
 @property (assign) float rating;

 - (id)initWithTitle:(NSString *)title rating:(float)rating;
 @end

RWTScaryBugData.m

@implementation RWTScaryBugData

@synthesize title = _title;
@synthesize rating = _rating;

- (id)initWithTitle:(NSString *)title rating:(float)rating {
    if ((self = [super init])) {
        self.title = title;
        self.rating = rating;
    }
    return self;
}

@end

我正在看这个初始化程序:

 - (id)initWithTitle:(NSString *)title rating:(float)rating {
 }

不是像那样写,我也可以这样写:

  - (RWTScaryBugData *)initWithTitle:(NSString *)title rating:(float)rating {
    }

谁能告诉我区别?或者,如果它真的不重要?

3 个答案:

答案 0 :(得分:12)

返回id而不是类是Objective-C中的约定,用于允许子类覆盖该初始化程序并返回其类型。例如,很长一段时间array上的NSArray类方法返回id,以便NSMutableArray可以覆盖该方法并返回一个可变数组,因此这两种方法都是可能的:

NSArray *array = [NSArray array];
NSMutableArray *mutableArray = [NSMutableArray array]; // Wouldn't be possible if the method returned (NSArray *)

问题在于您还可以说:

NSString *string = [NSArray array]; // bad

那将是一次挑战。 Apple引入了instancetype作为新的返回类型,它返回正在使用instancetype声明的类。今天,array方法返回instancetype,以便前面的例子超过typecheck,但不好的例子不会进行类型检查。

更多详情,请参阅NSHipster article on the subject

答案 1 :(得分:5)

在这些情况下,建议的返回类型为instancetype。 这包含在documentation

答案 2 :(得分:0)

除了能够重复使用(我的意思是复制/粘贴)初始化方法而不必修改返回类型之外,我认为没有任何特权。

实际上使用id实际上是一种不好的做法,因为没有使用id返回类型的编译时类型检查。实际上,惯例是使用instancetype而不是id(或类名),因为它具有两者的特权。