2015-05-06 61 views
6

我發現了很多類似的問題,但沒有一個幫助過。通用反序列化Gson類型令牌問題

這工作:

public class Assets<T> { 

public T getAndDeserializeAsset(String endpoint, String assetId, Client client){ 
    Response response = client.get(endpoint+assetId); 
    Gson gson = new Gson(); 
    T asset = gson.fromJson(response.body, new TypeToken<Email>(){}.getType()); 
    return asset; 
} 

}

這不:

public class Assets<T> { 

public T getAndDeserializeAsset(String endpoint, String assetId, Client client){ 
    Response response = client.get(endpoint+assetId); 
    Gson gson = new Gson(); 
    T asset = gson.fromJson(response.body, new TypeToken<T>(){}.getType()); 
    return asset; 
} 

}

我已經根據官方文檔做了,所以我不知道爲什麼它不起作用。

錯誤:

Exception in thread "main" java.lang.ClassCastException: com.rest.api.Response cannot be cast to model.Email 
at main.Main.main(Main.java:34) 

回答

0

有意義的是,你的Assets<T>實例必須是不Assets<Email>Assets<Response>一個實例,唯一的事情。您是否確定您的Assets實例是正確的類型?

另外,請記住,Gson不協變;當您使用TypeToken指定類型時,您必須使用您想要反序列化的確切類型。例如,如果您使用的類定義:

class Email extends Response { 

,然後使用:

new Assets<Response>(); 

因爲GSON是不是協變,也沒有辦法知道你真正想要的是一個Email

0

上面的代碼無法將值解釋爲類型,因爲Gson調用Assets.getClass()以獲取其類信息,但此方法返回一個原始類Assets.class。這意味着Gson無法知道這是一個類型爲Assets < Example>的對象,而不僅僅是簡單的Assets。

您可以通過爲泛型指定正確的參數化類型來解決此問題。您可以通過使用TypeToken類來完成此操作。

Type AssetsType = new TypeToken<Assets<Example>>() {}.getType(); 
gson.toJson(assets, AssetsType); 
gson.fromJson(json, AssetsType); 

的更多信息,請gson-user-guide