2011-09-24 31 views
20

我需要爲某些對象實現JSON序列化,並且在遇到與泛型集合集成時遇到了問題。Java JSON序列化 - 最佳實踐

所有序列化的類實現這個接口(的JSONObject來自this庫):

interface JSONSerializable{ 
    public JSONObject dump() throws JSONException //serializes object 
    public void load(JSONObject obj) throws JSONException //deserializes object 
} 
我的收藏基礎上的java.util.List看起來或多或少像這樣

代碼:

class AwesomeList<T extends JSONSerializable> implements JSONSerializable{ 
    private LinkedList<T> items = new LinkedList<T>(); 
    ... 
    ... 

    public JSONObject dump() throws JSONException { 
     JSONObject result = new JSONObject(); 
     JSONArray a = new JSONArray(); 
     for(T i : items){ 
      a.put(i.dump()); 
     } 
     result.put("items", a); 
     return result; 
    } 

    public void load(JSONObject obj) throws JSONException{ 
     //here is my problem 
    } 
} 

我的問題是:當我從JSONObject加載AwesomeList時,我需要創建它的元素,但這是不可能的,因爲java禁止我寫

T newItem = new T(); 
newItem.load(obj); 

我應該如何修改我的方法來完成這項任務?

+0

說實話,我不明白這是如何工作甚至已知類型。您是否將類名稱存儲在JSON數據包中? – Perception

+0

不,每個對象都知道如何從JSONObject加載它(事實上它只是關聯數組)。我更新了帖子以顯示我想要做什麼。 – KCH

回答

30

你被綁定到這個庫嗎? Google Gson非常受歡迎。我自己沒有使用泛型,但他們的頭版說Gson認爲對泛型的支持非常重要。

+2

gson可以很好地處理泛型。 – kingori

+3

上次我檢查了gson沒有處理循環引用..雖然更新可以修復..我找到[鏈接] http://jackson.codehaus.org/最好的。檢查我的這個問題,如何使用gson中的通用json轉換[鏈接] http://stackoverflow.com/questions/5528385/json-conversion-using-gson –

+0

GSON的使用非常非常非常簡單。 – schmijos

0

那麼,當它寫出來的文件,你知道什麼類T是,所以你可以存儲在dump。然後,在重新讀入時,可以使用反射動態調用它。

public JSONObject dump() throws JSONException { 
    JSONObject result = new JSONObject(); 
    JSONArray a = new JSONArray(); 
    for(T i : items){ 
     a.put(i.dump()); 
     // inside this i.dump(), store "class-name" 
    } 
    result.put("items", a); 
    return result; 
} 

public void load(JSONObject obj) throws JSONException { 
    JSONArray arrayItems = obj.getJSONArray("items"); 
    for (int i = 0; i < arrayItems.length(); i++) { 
     JSONObject item = arrayItems.getJSONObject(i); 
     String className = item.getString("class-name"); 
     try { 
      Class<?> clazzy = Class.forName(className); 
      T newItem = (T) clazzy.newInstance(); 
      newItem.load(obj); 
      items.add(newItem); 
     } catch (InstantiationException e) { 
      // whatever 
     } catch (IllegalAccessException e) { 
      // whatever 
     } catch (ClassNotFoundException e) { 
      // whatever 
     } 
    } 
4

正如其他人暗示的那樣,您應該考慮傾銷org.json的庫。這些日子已經過時了,試圖解決它的問題是浪費時間。

但是對於具體的問題;類型變量T只是沒有任何信息可以幫助你,因爲它只不過是編譯時信息。 相反,您需要傳遞實際的類(作爲'Class cls'參數),然後可以使用'cls.newInstance()'創建一個實例。

0

有沒有試過的json-io(https://github.com/jdereg/json-io)?

此庫允許您序列化/反序列化任何Java對象圖,包括其中包含循環的對象圖(例如A-> B,B-> A)。它不要求您的類實現任何特定的接口或從任何特定的Java類繼承。

除了對Java的序列化JSON(和JSON到Java),你可以用它來格式化(漂亮打印)JSON:

String niceFormattedJson = JsonWriter.formatJson(jsonString)