2010-08-23 59 views
8

這段代碼拋出異常:nil.to_json不能解析回nil?

x = nil 
jsoned = x.to_json 
puts 'x.to_json=' + jsoned.inspect 
puts 'back=' + JSON.parse(jsoned).inspect 

C:/ruby/lib/ruby/1.9.1/json/common.rb:146:in `parse': 706: unexpected token at 'null'  (JSON::ParserError) 
x.to_json="null" 
from C:/ruby/lib/ruby/1.9.1/json/common.rb:146:in `parse' 
from C:/dev/prototyping/appoxy_app_engine/test/temp.rb:10:in `<top (required)>' 
from -e:1:in `load' 
from -e:1:in `<main>' 

那是預期的行爲?我會認爲這應該工作?

回答

5

該問題不是專門用於nilto_json就像nil或單個字符串這樣簡單的東西不會產生完整的JSON表示。

例如像JSON.parse("hello".to_json)會產生類似的結果

如果我們有nil一個Hash其價值之一是將編碼和正確解碼:

>> h = {"name"=>"Mike", "info"=>nil} 
=> {"name"=>"Mike", "info"=>nil} 
>> h.to_json 
=> "{\"name\":\"Mike\",\"info\":null}" 
>> JSON.parse(h.to_json) 
=> {"name"=>"Mike", "info"=>nil} 
+9

你還沒有,本身,回答了這個問題。是to_json錯誤地產生「無效的」JSON,或者是JSON.parse無法解析「有效的」JSON?無論哪種方式,這不應該是紅寶石內的行爲。我希望序列化/反序列化能夠彼此保持一致,而不管底層媒體如何。 – ghayes 2013-06-05 22:52:02

+1

都不:to_json正確生成無效的JSON。當你調用to_json的單個值,例如nil時,你實際上是在說:「告訴我該值如何表示爲JSON值。」在某些情況下這是明智的做法,但非對象非數組值仍然不是有效的JSON文本。 – 2013-12-28 15:07:19

1

JSON不喜歡單一的對象,它是真正的序列化集合的物體。如果你嘗試這樣的事情,你可以看到它確實爲零對象生成了有效的JSON,並且可以對它們進行反序列化。

n = JSON.parse(JSON.generate([nil])) # => [nil] 
+1

在Ruby中,Array和Nil都是對象。 – weexpectedTHIS 2014-02-26 18:42:37

14

JSON解析器有一個「quirks模式」,它將解析單個JSON值。

>> nil.to_json 
=> "null" 
>> JSON.parse("null", {:quirks_mode => true}) 
=> nil 

它也適用於其他單值:

>> JSON.parse("12", {:quirks_mode => true}) 
=> 12 
>> JSON.parse("true", {:quirks_mode => true}) 
=> true 
>> JSON.parse(" \"string\" ", {:quirks_mode => true}) 
=> "string" 
+3

爲什麼ruby JSON lib不會將quirks_mode設置爲默認模式? quirks_mode是否有特殊的解析結果? quirks_mode是指默認模式+單個JSON值解析器? – agate 2013-11-19 03:23:58

+2

JSON文本的頂層必須是對象'{}'或數組''''。上面包含的單個值既不是對象也不是數組,因此不是嚴格解釋的JSON文本。怪癖模式允許解析單個值,如上所述 - 它不是默認值,因爲它處理非標準情況。 – 2013-12-28 01:25:43