كيفية التحقق مما إذا كان nsdictionary أو nsmutabletictionary يحتوي على مفتاح؟
-
03-10-2019 - |
سؤال
أحتاج إلى التحقق مما إذا كان DICT لديه مفتاح أم لا. كيف؟
المحلول
objectForKey
سيعود لا شيء إذا لم يكن هناك مفتاح.
نصائح أخرى
if ([[dictionary allKeys] containsObject:key]) {
// contains key
}
أو
if ([dictionary objectForKey:key]) {
// contains object
}
الإصدارات الأكثر حداثة من Objective-C و Clang لديها بناء جملة حديثة لهذا:
if (myDictionary[myKey]) {
}
ليس عليك التحقق من المساواة مع NIL ، لأنه يمكن تخزين كائنات الهدف غير NIL فقط في القواميس (أو المصفوفات). وجميع كائنات الهدف-C هي قيم الحقيقة. حتى @NO
, @0
, ، و [NSNull null]
تقييم صحيح.
تحرير: سويفت الآن شيء.
بالنسبة للسويفت ، ستحاول شيئًا مثل ما يلي
if let value = myDictionary[myKey] {
}
سيتم تنفيذ هذا الجملة فقط إذا كان Mykey في القولان وإذا تم تخزين القيمة في متغير القيمة. لاحظ أن هذا يعمل لقيم زائفة مثل 0.
if ([mydict objectForKey:@"mykey"]) {
// key exists.
}
else
{
// ...
}
عند استخدام قواميس JSON:
#define isNull(value) value == nil || [value isKindOfClass:[NSNull class]]
if( isNull( dict[@"my_key"] ) )
{
// do stuff
}
أحب إجابة فرنانديز على الرغم من أنك تطلب OBJ مرتين.
يجب أن يفعل هذا أيضًا (أكثر أو أقل مثل Martin's A).
id obj;
if ((obj=[dict objectForKey:@"blah"])) {
// use obj
} else {
// Do something else like creating the obj and add the kv pair to the dict
}
مارتن وهذا الإجابة على كل من العمل على iPad2 iOS 5.0.1 9A405
واحد سيتشا سيء للغاية الذي أهدر قليلاً من وقتي تصحيح الأخطاء - قد تجد نفسك مطالبة بالاشتراك التلقائي لمحاولة الاستخدام doesContain
الذي يبدو أنه يعمل.
إلا، doesContain
يستخدم مقارنة الهوية بدلاً من مقارنة التجزئة المستخدمة بواسطة objectForKey
لذلك إذا كان لديك قاموس مع مفاتيح السلسلة ، فسيعود لا إلى أ doesContain
.
NSMutableDictionary* keysByName = [[NSMutableDictionary alloc] init];
keysByName[@"fred"] = @1;
NSString* test = @"fred";
if ([keysByName objectForKey:test] != nil)
NSLog(@"\nit works for key lookups"); // OK
else
NSLog(@"\nsod it");
if (keysByName[test] != nil)
NSLog(@"\nit works for key lookups using indexed syntax"); // OK
else
NSLog(@"\nsod it");
if ([keysByName doesContain:@"fred"])
NSLog(@"\n doesContain works literally");
else
NSLog(@"\nsod it"); // this one fails because of id comparison used by doesContain
باستخدام Swift ، سيكون:
if myDic[KEY] != nil {
// key exists
}
نعم. هذا النوع من الأخطاء شائع جدًا ويؤدي إلى تعطل التطبيق. لذلك أستخدم إضافة NSDictionary في كل مشروع على النحو التالي:
//.H رمز الملف:
@interface NSDictionary (AppDictionary)
- (id)objectForKeyNotNull : (id)key;
@end
رمز الملف //M كما هو موضح أدناه
#import "NSDictionary+WKDictionary.h"
@implementation NSDictionary (WKDictionary)
- (id)objectForKeyNotNull:(id)key {
id object = [self objectForKey:key];
if (object == [NSNull null])
return nil;
return object;
}
@end
في الكود يمكنك استخدامه على النحو التالي:
NSStrting *testString = [dict objectForKeyNotNull:@"blah"];
للتحقق من وجود المفتاح في NSDictionary:
if([dictionary objectForKey:@"Replace your key here"] != nil)
NSLog(@"Key Exists");
else
NSLog(@"Key not Exists");
لأنه لا يمكن تخزين شيء في هياكل بيانات الأساس NSNull
في بعض الأحيان لتمثيل أ nil
. لان NSNull
هو كائن مفردة يمكنك التحقق منه لمعرفة ما إذا كان NSNull
هل القيمة المخزنة في القاموس باستخدام مقارنة المؤشر المباشر:
if ((NSNull *)[user objectForKey:@"myKey"] == [NSNull null]) { }
حل لويت 4.2
لذا ، إذا كنت تريد فقط الإجابة على السؤال عما إذا كان القاموس يحتوي على المفتاح ، اسأل:
let keyExists = dict[key] != nil
إذا كنت تريد القيمة وأنت تعرف أن القاموس يحتوي على المفتاح ، قل:
let val = dict[key]!
ولكن ، إذا ، كما يحدث عادة ، لا تعرف أنه يحتوي على المفتاح - فأنت تريد جلبه واستخدامه ، ولكن فقط إذا كان موجودًا - استخدم شيئًا مثل if let
:
if let val = dict[key] {
// now val is not nil and the Optional has been unwrapped, so use it
}
أود أن أقترح عليك تخزين نتيجة البحث في متغير مؤقت ، واختبار ما إذا كان متغير Temp لا شيء ثم استخدامه. بهذه الطريقة لا تنظر إلى نفس الكائن مرتين:
id obj = [dict objectForKey:@"blah"];
if (obj) {
// use obj
} else {
// Do something else
}
كما اقترح أديرائيل objectForKey
للتحقق من الوجود الرئيسي ولكن عند الاتصال objectForKey
في القاموس الباطل ، يتم تحطم التطبيق لذلك قمت بإصلاح هذا من الطريق التالي.
- (instancetype)initWithDictionary:(NSDictionary*)dictionary {
id object = dictionary;
if (dictionary && (object != [NSNull null])) {
self.name = [dictionary objectForKey:@"name"];
self.age = [dictionary objectForKey:@"age"];
}
return self;
}
if ([MyDictionary objectForKey:MyKey]) {
// "Key Exist"
}