javascript - जेएसओएन ने इन्फिनिटी और नाएन छोड़ा; ईसीएमएस्क्रिप्ट में JSON स्थिति?




ecma262 (6)

ऐसा इसलिए हो सकता है क्योंकि जेएसओएन का उद्देश्य डेटा इंटरचेंज प्रारूप होना है जिसका उपयोग विभिन्न प्लेटफार्मों में किया जा सकता है और नाएन / इन्फिनिटी इसे कम पोर्टेबल बना देगा।

कोई विचार क्यों JSON ने NaN और +/- अनंतता छोड़ी? यह अजीब परिस्थिति में जावास्क्रिप्ट रखता है जहां ऑब्जेक्ट्स अन्यथा धारावाहिक होते हैं, अगर वे NaN या +/- अनंत मान रखते हैं।

ऐसा लगता है कि इसे पत्थर में डाला गया है: RFC4627 और ECMA-262 (धारा 24.3.2, JSON.stringify, नोट 4, अंतिम संपादन पर पृष्ठ 507 देखें):

सीमित संख्याएं जैसे कि ToString(number) कॉल करके ToString(number) । साइन के बावजूद NaN और अनंतता स्ट्रिंग null रूप में दर्शायी जाती है।


क्या आप शून्य ऑब्जेक्ट पैटर्न को अनुकूलित कर सकते हैं, और आपके JSON में ऐसे मानों का प्रतिनिधित्व करते हैं

"myNum" : {
   "isNaN" :false,
   "isInfinity" :true
}

फिर जांच करते समय, आप प्रकार की जांच कर सकते हैं

if (typeof(myObj.myNum) == 'number') {/* do this */}
else if (myObj.myNum.isNaN) {/* do that*/}
else if (myObj.myNum.isInfinity) {/* Do another thing */}

मुझे जावा में पता है कि आप ऐसी चीज को लागू करने के लिए क्रमबद्ध तरीकों को ओवरराइड कर सकते हैं। सुनिश्चित नहीं है कि आपका सीरियलाइजिंग कहां से है, इसलिए मैं धारावाहिक तरीकों में इसे कार्यान्वित करने के तरीके के बारे में विवरण नहीं दे सकता।


यदि आपके पास सीरियलाइजेशन कोड तक पहुंच है तो आप इन्फिनिटी को 1.0e + 1024 के रूप में प्रदर्शित कर सकते हैं। एक्सपोनेंट एक डबल में प्रतिनिधित्व करने के लिए बहुत बड़ा है और जब deserialized यह अनंतता के रूप में प्रतिनिधित्व किया जाता है। वेबकिट पर काम करता है, अन्य जेसन पार्सर्स के बारे में अनिश्चित!


यदि मेरे जैसा आप धारावाहिक कोड पर कोई नियंत्रण नहीं रखते हैं, तो आप नाक के कुछ हिस्सों को नाक या किसी अन्य मूल्य के साथ बदलकर नाक मानों से निपट सकते हैं:

$.get("file.json", theCallback)
.fail(function(data) {
  theCallback(JSON.parse(data.responseText.replace(/NaN/g,'null'))); 
} );

संक्षेप में, जब मूल जेसन पार्सर एक अवैध टोकन का पता लगाता है तो .fail कॉल किया जाएगा। फिर अमान्य टोकन को प्रतिस्थापित करने के लिए एक स्ट्रिंग प्रतिस्थापन का उपयोग किया जाता है। मेरे मामले में यह serialiser के लिए NaN मान वापस करने के लिए एक अपवाद है, इसलिए यह विधि सबसे अच्छा तरीका है। यदि परिणाम में सामान्य रूप से अमान्य टोकन होता है तो आप $ .get का उपयोग न करने के लिए बेहतर होंगे, लेकिन JSON परिणाम मैन्युअल रूप से पुनर्प्राप्त करने और हमेशा स्ट्रिंग प्रतिस्थापन को चलाने के लिए।


स्ट्रिंग्स "इन्फिनिटी", "-इफिनिटी", और "नाएन" जेएस में अपेक्षित मूल्यों के लिए सभी कॉरर्स हैं। इसलिए मैं जेएसओएन में इन मानों का प्रतिनिधित्व करने का सही तरीका तर्क दूंगा।

> +"Infinity"
Infinity

> +"-Infinity"
-Infinity

> +"NaN"
NaN

यह सिर्फ एक शर्म की बात है JSON.stringify डिफ़ॉल्ट रूप से ऐसा नहीं करता है। लेकिन एक तरीका है:

> JSON.stringify({ x: Infinity }, function (k,v) { return v === Infinity ? "Infinity" : v; })
"{"x":"Infinity"}"

Infinity और NaN कीवर्ड या कुछ खास नहीं हैं, वे वैश्विक वस्तु (जैसे undefined ) पर गुण हैं और इस तरह बदला जा सकता है। यही कारण है कि जेएसओएन ने उन्हें spec में शामिल नहीं किया है - संक्षेप में यदि आप eval(jsonString) या JSON.parse(jsonString) करते हैं तो किसी भी वास्तविक JSON स्ट्रिंग का एक ही परिणाम EcmaScript में होना चाहिए।

अगर इसकी अनुमति थी तो कोई व्यक्ति कोड को इंजेक्ट कर सकता था

NaN={valueOf:function(){ do evil }};
Infinity={valueOf:function(){ do evil }};

एक मंच (या जो कुछ भी) में और फिर उस साइट पर किसी भी जेसन उपयोग से समझौता किया जा सकता है।





ecma262