BAD_ACCESS

おもにiOS、ときどき変な電子工作、ガジェット話。

KVC(Key-Value Coding)とは何か(2):KeyPath

前回のメモKVC(Key-Value Coding)とは何か(1) - BAD_ACCESS

「KVC」でも重要な要素であるKeyPathについてメモ。
参考書籍は前回に引き続き「詳解Objective-C 2.0」詳解 Objective-C 2.0 第3版

<KeyPath(キーパス)とは何か>

Pesonクラスのオブジェクトをメンバ変数に持つGroupクラスを考える。
まずはPerson.h(前回と同じ)

@interface Person : NSObject {
    NSString *name;
    NSString *email;
    int          *age;
}
@end

Group.h

@interface Group : NSObject {
    Person *leader;
    NSMutableArray *members;
}
@end

GroupクラスのオブジェクトであるaGroupのリーダーの名前にアクセスすることを考える。

id aLeader = [aGroup valueForKey:@"leader"];
id name = [aLeader valueForKey:@"name"]; 

KeyPathを使うことで上記と全く同じ意味で下記のように表記することができる。

id name = [aGroup valueForKey:@"leader.name"];

(Keyをドットでつないだ文字列をKeyPath(キーパス)という)

<「Key」または「KeyPath」を使ったときに注意する点>

@"leader.name"というKeyPathを指定してオブジェクトにアクセスする場合と@"member.name"というKeyPathを指定してアクセスする場合、どのような違いがあるか。
@"leader.name"は結果がひとつに決まるが@"member.name"を指定しても結果はひとつに決まるとは限らない。(対多リレーションシップ)
アクセスするとき(値を取得するとき)は結果が複数の場合であれば配列(または集合)で返ってくるが、値をセットするときは注意が必要である。
下記のようなGroupクラス「taroGroup」オブジェクトがあったとする。

このオブジェクトに対して、下記の操作を行った場合、結果はどうなるだろうか。

[taroGroup setValue:@"Jiro" forKeyPath:@"members.name"];


なんとmembers全員の名前がJiroになってしまう。
各KeyまたはKeyPathに対応するプロパティを注意して確認しておく必要がある。