मैं एक NSSON में JSON स्ट्रिंग को कैसे निष्क्रिय कर सकता हूं? (IOS 5+ के लिए)


154

मेरे iOS 5 ऐप में, मेरे पास NSStringएक JSON स्ट्रिंग है। मुझे लगता है कि JSON स्ट्रिंग प्रतिनिधित्व एक मूल NSDictionaryवस्तु में deserialize करना चाहते हैं ।

 "{\"password\" : \"1234\",  \"user\" : \"andreas\"}"

मैंने निम्नलिखित दृष्टिकोण की कोशिश की:

NSDictionary *json = [NSJSONSerialization JSONObjectWithData:@"{\"2\":\"3\"}"
                                options:NSJSONReadingMutableContainers
                                  error:&e];  

लेकिन यह एक रनटाइम त्रुटि फेंकता है। मैं क्या गलत कर रहा हूं?

-[__NSCFConstantString bytes]: unrecognized selector sent to instance 0x1372c 
*** Terminating app due to uncaught exception 'NSInvalidArgumentException',
reason: '-[__NSCFConstantString bytes]: unrecognized selector sent to instance 0x1372c'

यह मेरा दृष्टिकोण था: NS सहकर्मी * JSON = [NSJSONSerialization JSONObjectWithData: @ "{\" 2 \ ": \" 3 \ "} विकल्प: NSJSONReadingMutableMontainers त्रुटि: & e]; i get: 2011-12-22 17: 18: 59.300 Pi9000 [938: 13803] - [__ NSCFConstantString बाइट्स]: गैर-मान्यता प्राप्त चयनकर्ता को उदाहरण के लिए भेजा गया 0x1372c 2011-12-22: 17: 59.302 Pi9000 [938: 13803] *** अनकहा अपवाद 'NSInvalidArgumentException' अपवाद के कारण ऐप समाप्त करना, कारण: '- [__ NSCFConstantString बाइट्स]: अपरिचित चयनकर्ता को उदाहरण के लिए भेजा गया 0x1372c
Andreas

मेरा जवाब देखें कि स्विफ्ट 3 और स्विफ्ट 4 के लिए एक शब्दकोश में JSON स्ट्रिंग को
डिसेर्बलाइज

जवाबों:


335

ऐसा लगता है कि आप एक NSStringपैरामीटर पास कर रहे हैं, जहां आपको एक NSDataपैरामीटर पास करना चाहिए :

NSError *jsonError;
NSData *objectData = [@"{\"2\":\"3\"}" dataUsingEncoding:NSUTF8StringEncoding];
NSDictionary *json = [NSJSONSerialization JSONObjectWithData:objectData
                                      options:NSJSONReadingMutableContainers 
                                        error:&jsonError];

@ अब, मैं यहाँ किस त्रुटि का उपयोग कर सकता हूँ? (op इसका उल्लेख नहीं करता है)

धन्यवाद ... यह एक मदद की! और +1
जयप्रकाश दुबे

धन्यवाद, यह काम किया। हालांकि, XCode 5 के nilबजाय त्रुटि के रूप में उपयोग करना&e
माइकल हो चुम

3
मुझे ऑब्जेक्टिव सी पसंद है। अपने स्ट्रिंग को कच्ची बाइट्स में एनकोड करें और फिर उन्हें एनएसएसट्रेस और एनएसएनट्रस पर वापस डिकोड करें। यह स्पष्ट है, है ना?
वाहोटम

1
@ अपने आवेदन के बाहर कहीं से एक स्ट्रिंग के रूप में JSON प्राप्त करने के लिए अपने सामान्य
पते

37
NSData *data = [strChangetoJSON dataUsingEncoding:NSUTF8StringEncoding];
NSDictionary *jsonResponse = [NSJSONSerialization JSONObjectWithData:data
                                                             options:kNilOptions
                                                               error:&error];

उदाहरण के लिए आपके पास strChangetoJSON NSStringमें विशेष वर्ण हैं NSString। फिर आप उपरोक्त कोड का उपयोग करके उस स्ट्रिंग को JSON प्रतिक्रिया में बदल सकते हैं।


6

मैंने @ उत्तर से श्रेणी बनाई है

@implementation NSString (Extensions)
- (NSDictionary *) json_StringToDictionary {
    NSError *error;
    NSData *objectData = [self dataUsingEncoding:NSUTF8StringEncoding];
    NSDictionary *json = [NSJSONSerialization JSONObjectWithData:objectData options:NSJSONReadingMutableContainers error:&error];
    return (!json ? nil : json);
}
@end

इसे इस तरह उपयोग करें,

NSString *jsonString = @"{\"2\":\"3\"}";
NSLog(@"%@",[jsonString json_StringToDictionary]);

यह मेरी समझ है कि errorइन मामलों में परीक्षण नहीं करना सबसे अच्छा अभ्यास है , लेकिन यह परीक्षण करने के लिए कि वापसी मूल्य शून्य है या नहीं लौटने से पहले। यानी return json ?: nil; माइनर नाइटपिक, लेकिन ध्यान देने योग्य है, मुझे लगता है।
माइक

@ माय, मुझे लगता है कि मूल्य की परवाह किए बिना "त्रुटि" की जांच करना ठीक है? क्योंकि, अगर कोई त्रुटि है तो हम nilतुरंत वापस लौट रहे हैं ।
हेमांग

Apple के डॉक्स के अनुसार "जब संदर्भ से पारित त्रुटियों से निपटते हैं, तो यह देखने के लिए कि क्या कोई त्रुटि हुई है, यह देखने के लिए विधि के रिटर्न मूल्य का परीक्षण करना महत्वपूर्ण है। केवल यह देखने के लिए परीक्षण न करें कि त्रुटि सूचक को इंगित करने के लिए सेट किया गया था या नहीं। एक त्रुटि।" developer.apple.com/library/ios/documentation/Cocoa/Conceptual/… मेरा मानना ​​है कि ऐसा इसलिए है क्योंकि ऐसे मामले हो सकते हैं जहां कोई त्रुटि नहीं होती है और विधि एक मान लौटाती है, लेकिन स्मृति जहां त्रुटि सूचक इंगित करती है के लिए लिखा है, तो आपको लगता है कि एक त्रुटि मौजूद है।
माइक

मुझे मेरे एक पूर्व प्रश्न में ध्यान में रखा गया था: "चर असंवैधानिक है। इसका मतलब है कि उस पते पर मूल्य अपरिभाषित है, इसलिए मान को बदलने का कोई मतलब नहीं है ... क्योंकि कोई गारंटी नहीं है कि विधि नहीं लिखेंगे। यदि कोई त्रुटि नहीं होती है, तो पते में कचरा डालें, Apple के डॉक्स का कहना है कि त्रुटि चर के मूल्य का परीक्षण करना असुरक्षित है। " stackoverflow.com/questions/25558442/…
माइक

1
@ माइक, ओह महान, पता करने के लिए अच्छा है! संदर्भ के लिए धन्यवाद। मैं जल्द ही इसे अपडेट करूंगा।
हेमांग

5

स्विफ्ट 3 और स्विफ्ट 4 के साथ, Stringएक विधि कहा जाता है data(using:allowLossyConversion:)data(using:allowLossyConversion:)निम्नलिखित घोषणा है:

func data(using encoding: String.Encoding, allowLossyConversion: Bool = default) -> Data?

किसी दिए गए एन्कोडिंग का उपयोग करके इनकोड किए गए स्ट्रिंग का प्रतिनिधित्व करने वाला डेटा लौटाता है।

स्विफ्ट 4 के साथ, Stringके data(using:allowLossyConversion:)साथ संयोजन के रूप में इस्तेमाल किया जा सकता JSONDecoder'एस decode(_:from:)के लिए एक शब्दकोश में JSON स्ट्रिंग deserialize करने के लिए।

इसके अलावा, स्विफ्ट और स्विफ्ट 3 4 के साथ, Stringके data(using:allowLossyConversion:)भी साथ संयोजन के रूप में इस्तेमाल किया जा सकता JSONSerialization'एस json​Object(with:​options:​)के लिए एक शब्दकोश में JSON स्ट्रिंग deserialize करने के लिए।


# 1। स्विफ्ट 4 समाधान

स्विफ्ट 4 के साथ, JSONDecoderएक विधि कहा जाता है decode(_:from:)decode(_:from:)निम्नलिखित घोषणा है:

func decode<T>(_ type: T.Type, from data: Data) throws -> T where T : Decodable

दिए गए JSON प्रतिनिधित्व से दिए गए प्रकार के एक शीर्ष-स्तरीय मान को डिकोड करता है।

नीचे दिए गए प्लेग्राउंड कोड से पता चलता है कि JSON फॉर्मेट से कैसे उपयोग किया जाए data(using:allowLossyConversion:)और कैसे decode(_:from:)प्राप्त किया जाए :DictionaryString

let jsonString = """
{"password" : "1234",  "user" : "andreas"}
"""

if let data = jsonString.data(using: String.Encoding.utf8) {
    do {
        let decoder = JSONDecoder()
        let jsonDictionary = try decoder.decode(Dictionary<String, String>.self, from: data)
        print(jsonDictionary) // prints: ["user": "andreas", "password": "1234"]
    } catch {
        // Handle error
        print(error)
    }
}

# 2। स्विफ्ट 3 और स्विफ्ट 4 समाधान

स्विफ्ट 3 और स्विफ्ट 4 के साथ, JSONSerializationएक विधि कहा जाता है json​Object(with:​options:​)json​Object(with:​options:​)निम्नलिखित घोषणा है:

class func jsonObject(with data: Data, options opt: JSONSerialization.ReadingOptions = []) throws -> Any

दिए गए JSON डेटा से एक फाउंडेशन ऑब्जेक्ट लौटाता है।

नीचे दिए गए प्लेग्राउंड कोड से पता चलता है कि JSON फॉर्मेट से कैसे उपयोग किया जाए data(using:allowLossyConversion:)और कैसे json​Object(with:​options:​)प्राप्त किया जाए :DictionaryString

import Foundation

let jsonString = "{\"password\" : \"1234\",  \"user\" : \"andreas\"}"

if let data = jsonString.data(using: String.Encoding.utf8) {
    do {
        let jsonDictionary = try JSONSerialization.jsonObject(with: data, options: []) as? [String : String]
        print(String(describing: jsonDictionary)) // prints: Optional(["user": "andreas", "password": "1234"])
    } catch {
        // Handle error
        print(error)
    }
}

3

स्विफ्ट 2.2 के लिए अबिज़र्न कोड का उपयोग करना

let objectData = responseString!.dataUsingEncoding(NSUTF8StringEncoding)
let json = try NSJSONSerialization.JSONObjectWithData(objectData!, options: NSJSONReadingOptions.MutableContainers)
हमारी साइट का प्रयोग करके, आप स्वीकार करते हैं कि आपने हमारी Cookie Policy और निजता नीति को पढ़ और समझा लिया है।
Licensed under cc by-sa 3.0 with attribution required.