その後のその後

iOSエンジニア 堤 修一のブログ github.com/shu223

【Xcode 6】delegateをセットするところで「incompatible type 'id'」なるwarningが出る件

たとえば下記のように、delegate プロトコルと、それをプロパティに持つクラスを定義し、

@protocol HogeManagerDelegate <NSObject>
@end

@interface HogeManager : NSObject
@property (nonatomic, weak) id<HogeManagerDelegate> delegate;
@end


HogeViewController で下記のように `setDelegate:` するとします。

[[HogeManager sharedManager] setDelegate:self];


で、これを Xcode 6 でビルドすると、

warning: sending 'HogeViewController *const __strong' to parameter of incompatible type 'id<NSFileManagerDelegate>'
    [[HogeManager sharedManager] setDelegate:self];

こんな warning が出てきます。


全然 NSFileManagerDelegate とか関係ない(プロパティにも親クラスにもない、プロジェクトで全く明示的には使ってない)し、Xcode 5 では warning 出てなかったし・・・ということで、当初はスルーしてたのですが、やはり気になるので対処方法を検討してみました。

対処法

+ (id)sharedManager;

となっていたのを、

+ (instancetype)sharedManager;

とすればOKでした。

instancetypeについて

instancetype というのは、

instancetype型は、上で述べたような「レシーバのクラス==返り値オブジェクトのクラス」となることを明示的に示すための、メソッドの返り値にのみ使える型です。

Objective-Cにおけるinstancetype型について | Takebayashi.Asia


ということで、問題のwarningは、明示的に戻り値のオブジェクトのクラスが指定できてないよ、ということを知らせてくれていたわけです。


そういえば、今回の iOS 8 の API diff も、この戻り値 id > instancetypes への変更が盛りだくさんでしたね。。