2013-05-28 68 views
59

我改變從org.json傑克遜我的JSON庫,我想遷移以下代碼:傑克遜如何將JsonNode轉換爲ArrayNode而不投射?

JSONObject datasets = readJSON(new URL(DATASETS)); 
JSONArray datasetArray = datasets.getJSONArray("datasets"); 

現在在傑克遜我有以下幾點:

ObjectMapper m = new ObjectMapper(); 
JsonNode datasets = m.readTree(new URL(DATASETS));  
ArrayNode datasetArray = (ArrayNode)datasets.get("datasets"); 

但是我不知道像那裏的演員一樣,有沒有可能是ClassCastExceptionorg.json有沒有相當於getJSONArray的方法,這樣我就有適當的錯誤處理,以防它不是數組?

+0

不幸的是,我不能使用完整的映射,因爲數據不固定字段名稱。 –

+1

如果字段名稱來自有限集合,您可能需要定義一個以所有這些集合爲特徵的類,並使用解串器的'FAIL_ON_UNKNOWN_PROPERTIES'功能獲取未使用字段中返回的空值。但是,如果字段名稱集相對有限,那當然只是一個選項。 – fvu

+0

嗯,我認爲這個解決方案並不適合我的情況,但我會記住它,以防我會遇到預先知道的有限集合的問題! –

回答

146

是的,傑克遜手動語法分析器的設計與其他庫非常不同。尤其是,您會注意到JsonNode具有大部分通常與其他API的陣列節點關聯的功能。因此,您不需要投入ArrayNode即可使用。這裏有一個例子:

JSON:

{ 
    "objects" : ["One", "Two", "Three"] 
} 

代碼:

final String json = "{\"objects\" : [\"One\", \"Two\", \"Three\"]}"; 

final JsonNode arrNode = new ObjectMapper().readTree(json).get("objects"); 
if (arrNode.isArray()) { 
    for (final JsonNode objNode : arrNode) { 
     System.out.println(objNode); 
    } 
} 

輸出:

「一個」
‘二’
‘三公’

注意使用isArray以驗證該節點實際上是迭代前一個數組。如果你對你的數據結構有絕對的信心,那麼這個檢查就沒有必要了,但是如果你需要的話,這個檢查是可用的(這與大多數其他JSON庫沒有什麼不同)。

+1

你節省了我的時間。謝謝! –

1

在org.json中是否存在一個與getJSONArray等價的方法,以便在出現不是數組的情況下有適當的錯誤處理?

這取決於您的輸入;即您從URL中獲取的內容。如果「datasets」屬性的值是關聯數組而不是普通數組,則會得到ClassCastException

但是再次,您的舊版本的正確性取決於輸入。在新版本投出ClassCastException的情況下,舊版本將拋出JSONException。參考:http://www.json.org/javadoc/org/json/JSONObject.html#getJSONArray(java.lang.String)

+0

好的,所以我可以抓到一個ClassCastException,謝謝!對於我的口味來說,它比一個特定的JsonException稍微優雅一點,但如果不可行的話,那還是不錯的。 –