NSDictionary
にはobjectForKey:
などの方法でアクセスする必要があります。しかし、NSDictionary
へのドット記法アクセスを許可することは可能であり、学習目的のために、これは誰かにとって興味深いかもしれない。たとえば、AFNetworking
を使用して大きなJSON辞書を取得している場合でも、このメソッドを使用するとコードのアクセスと可読性が向上します。
これは私のソリューションです:
DictionaryProperties.h:(クラスはプロパティへのアクセスのためのNSDictionaryのをラップ)
@interface DictionaryProperties : NSObject{
NSMutableDictionary* _backingDict;
}
@property (nonatomic, strong) NSMutableDictionary* backingDict;
+ (DictionaryProperties*) allocWithDictionary:(NSDictionary*)dict;
@end
DictionaryProperties.m:
#import "DictionaryProperties.h"
@implementation DictionaryProperties
@synthesize backingDict = _backingDict;
- (id) initWithDictionary:(NSDictionary*)dict {
if (self) {
if ([dict isKindOfClass:[NSMutableDictionary class]]) {
self.backingDict = (id)dict;
} else {
self.backingDict = [[NSMutableDictionary alloc] initWithDictionary:dict];
}
}
return self;
}
+ (DictionaryProperties*) allocWithDictionary:(NSDictionary*)dict {
return [[DictionaryProperties alloc] initWithDictionary:dict];
}
- (void)forwardInvocation:(NSInvocation *)invocation
{
NSString* key = NSStringFromSelector(invocation.selector);
invocation.selector = @selector(objectForKey:);
[invocation setArgument:&key atIndex:2];
if ([self.backingDict objectForKey:key]) {
[invocation invokeWithTarget:self.backingDict];
} else {
[self doesNotRecognizeSelector:invocation.selector];
}
}
- (NSMethodSignature *)methodSignatureForSelector:(SEL)aSelector{
return [self.backingDict methodSignatureForSelector:@selector(objectForKey:)];
}
@end
ExampleDictContent.h:(クラス辞書の中に何があるかを宣言する)
#import "DictionaryProperties.h"
@interface ExampleDictContent : DictionaryProperties
@property (strong, nonatomic) NSString* someData;
@property (strong, nonatomic) NSString* someOtherData;
@end
@implementation ExampleDictContent
@end
使用方法:(辞書のシンプルな宣言、ラッパーや財産へのアクセスの割り当て)
#import "ExampleDictContent.h"
NSDictionary* d = [NSDictionary dictionaryWithObjects:NSArray arrayWithObjects:@"someData content", @"someOtherData content", nil
forKeys:NSArray arrayWithObjects:@"someData", @"someOtherData", nil];
ExampleDictContent* dictWProps = [ExampleDictContent allocWithDictionary:d];
NSLog(dictWProps.someData);
NSLog(dictWProps.someData);
これが印刷されます:NSDictionary
にアクセスするためのファサードとして
someData content
someOtherData content
そこで、基本的DictionaryProperties
作品を。 メソッド呼び出しを辞書のgetObjectForKey:
コールに変換するには、forwardInvocation
を使用します。私が気に入っているのは、辞書の自動補完が可能で、アクセスするキー(ExampleDictContent.h
ファイル)を明示的に宣言することもできます。このソリューションはプロパティへの書き込みアクセスを許可していませんが、以下のリンクに示すように追加できます。
この解決方法の一部は、karstenlitsche's solutionからインスピレーションを受けています。主な違いは、このソリューションはカテゴリの代わりにサブクラスに基づいていることです。
私はあなたがカテゴリを使ってドット表記法を使用できるようにするつもりです。 –
@ RichardJ.RossIII私はあなたがカテゴリーで答えなければならないとは思わない。いくつかのObj-C機能を示していますが、これはかなり悪い習慣です。おそらく、 'NSObject'のサブクラスであるモデルオブジェクトを提案するほうが良いアプローチでしょう。 –
コンパイラがドットを拒否するので、あなたが ' - (id)valueForUndefinedKey: 'を上書きして何かできることは疑問です... – JustSid