2016-05-10 3 views
0

私のプロジェクトでは、SwiftとObjective Cの両方を使用しています。Objective Cで書かれたシングルトンを、NSDictionary型のプロパティとして持っています。[NSObject:AnyObject]をチェックする! SwiftのNSNullです。

@property(nonatomic, strong) NSDictionary *currentDictionary; 

これは私のプロジェクト全体で使用されている古いクラスです。私は私が直面しています問題はcurrentDictionaryがサーバからのデータを使用して設定されていることである。この

if let dict = DataManager.sharedManager().currentDictionary 
{ 
    // 
} 

ようスウィフトクラスでこのクラスを使用しようとしています。時には、これはObjective Cのクラスでは

かもしれないが、私は、次のチェック

if ([currentDictionary isKindOfClass: [NSNull class]]) 
{ 
    // Do nothing 
} 

で状況を処理することができますが、私はスウィフトで同様のチェックを実装する方法を確認していません。 nsnullをは

を「常に失敗した 『『無関係なタイプに』私は、次の

if let data = DataManager.sharedManager().currentDictionary as? NSNull 
{ 
    return 
} 

を試みたが、それは動作しませんし、また、私は、コンパイラの警告を取得:

[ANYOBJECT NSObjectの]」からキャストを』!

これはdicitonary内のNull値が 'AnyObject'であるため、チェックしたいタイプにキャストしようとするので、これとは異なります。

することは、誰かがあなたがcurrentDictionary天気を検証したい場合は、使用することができ、nilかではない、適切

+2

「NSDictionary」は、決して*** NSNull型でなければなりません。その内容は辞書自体ではありません。 – luk2302

+1

この投稿はおそらくあなたのために便利ですhttp://stackoverflow.com/questions/24026609/detect-a-null-value-in-nsdictionary – HDT

+0

@ luk2302 ..はい、そうすべきではありません。私は同じことをサーバー側に伝えました。しかし、私はクライアントで安全性チェックを追加したいと思います。 – humblePilgrim

答えて

1

をこのような状況を処理する方法上の任意のポインタを提供していただけます。

guard let currentDictionary = DataManager.sharedManager().currentDictionary else { 
    return 
} 

場合if-elseguard-else文を交換してくださいあなたは早く帰りたくありません。

あなたはcurrentDictionaryの内容を検証したい場合はNSNullかではありません。すべての

if let value = DataManager.sharedManager().currentDictionary["key"] { 
    // do something with value 
} 
+0

私はガードステートメントを試しましたが、それは同様に役立たない。実際にはNSNullオブジェクトが存在するため、失敗した場合はnilをチェックすると思います。 – humblePilgrim

+0

Guard DataManager.sharedManager()を使用するとどうなりますか?currentDictionaryはNSNull else {return} 'ですか? – mro

+0

同じ警告が生成されます。 – humblePilgrim

2

まず、変数はNSDictionaryは、NSDictionaryにそのタイプを設定しないことを何か他のものを含めることができます。 Swiftは型安全です。宣言された型を信頼します。

最も簡単な回避策はObjective-Cでidにすることです。

次にスウィフトにあなたは、単にすることができます

guard let data = DataManager.sharedManager().currentDictionary as? NSDictionary else { 
    return 
} 

あなたは元のコードを変更することができない場合は、単に例えば、カテゴリを使用して、正しいタイプでスウィフトアクセサを作成します

@interface DataManager (Swift) 

// solution 1, will be converted to AnyObject in Swift 
- (id)currentDictionaryForSwift1; 

// solution 2, let's handle NSNull internally, don't propagate it to Swift 
- (NSDictionary *)currentDictionaryForSwift2; 

@end 

@implementation DataManager 

- (id)currentDictionaryForSwift1 { 
    return self.currentDictionary; 
} 

- (NSDictionary *)currentDictionaryForSwift2 { 
    if (self.currentDictionary == [NSNull null]) { 
     return nil; 
    } 

    return self.currentDictionary; 
}  

@end 

私は内部NSNullを処理するために、あなたをお勧めします。 nilNSNullを別々に処理する必要はありません。

あなたが実際にゲッターですでにそれを解決することができます:あなたが見ることができるように、そこに複数のソリューションがあるが、最善の解決策は、あなたのObjにも改善すべき

- (NSDictionary *)currentDictionary { 
    if (_currentDictionary == [NSNull null]) { 
     return nil; 
    } 

    return _currentDictionary; 
} 

やセッター

- (void)setCurrentDictionary:(NSDictionary *)currentDictionary { 
    if (currentDictionary == [NSNull null]) { 
     _currentDictionary = nil; 
    } else { 
     _currentDictionary = currentDictionary; 
    } 
} 

に-Cコード。 NSNullnilの違いは、ローカルで処理され、伝播されないようにしてください。

関連する問題