簡體   English   中英

引起:java.lang.ClassCastException:使用Generic Type時,libcore.reflect.ParameterizedTypeImpl無法強制轉換為java.lang.Class

[英]Caused by: java.lang.ClassCastException: libcore.reflect.ParameterizedTypeImpl cannot be cast to java.lang.Class when use Generic Type

我做了一個類擴展AsyncTask來解析Json使用Gson,因為輸入可以是很多類我使用泛型類:

public class ApiResponse<T> extends AsyncTask...

我需要知道T類的類型來傳遞Gson:

(1)

Class<T> clazz =
    (Class<T>)((ParameterizedType)
        getClass().getGenericSuperclass())
    .getActualTypeArguments()[0];

new Gson().fromJson(reader, clazz);

但是,這里的T可以是一個有很多類型的類,所以有一段時間我傳遞類:

(2)

public class DataMessage<T> implements Serializable{...}

有了這些類有這種格式,我收到了一個異常引起的:

java.lang.ClassCastException: libcore.reflect.ParameterizedTypeImpl cannot be cast to java.lang.Class

在(1)

在這種情況下我該怎么辦?

更新:

public class DataMessage<T> implements Serializable{

    @SerializedName("pagination")
    private Pagination pagination;
    @SerializedName("meta")
    private Message meta;
    @SerializedName("data")
    private T data;

    public DataMessage(T data) {
        this.data = data;
    }

    public Pagination getPagination() {
        return pagination;
    }

    public void setPagination(Pagination pagination) {
        this.pagination = pagination;
    }

    public Message getMeta() {
        return meta;
    }

    public void setMeta(Message meta) {
        this.meta = meta;
    }

    public T getData() {
        return data;
    }

    public void setData(T data) {
        this.data = data;
    }

    public class Pagination {
        @SerializedName("next_max_tag_id")
        public String nextMaxTagId;
        @SerializedName("deprecation_warning")
        public String deprecationWarning;
        @SerializedName("next_max_id")
        public String nextMaxId;
        @SerializedName("next_min_id")
        public String nextMinId;
        @SerializedName("min_tag_id")
        public String minTagId;
        @SerializedName("next_url")
        public String nextUrl;
    }

    public class Message {
        @SerializedName("error_type")
        public String errorType;
        @SerializedName("code")
        public int code;
        @SerializedName("error_message")
        public String error_message;
    }
}

當我需要使用Gson解析特定類的JSON時,我以這種方式使用GsonBuilder

GsonBuilder gsonBuilder = new GsonBuilder();

gsonBuilder.registerTypeAdapter(Date.class, new JsonDeserializer<Date>() {
   public Date deserialize(JsonElement json, Type typeOfT, JsonDeserializationContext context) throws JsonParseException {
        try{
           return new Date( json.getAsJsonPrimitive().getAsLong()*1000L );
        }catch( Exception e ){
            return null;
        }

   }
});

Gson gson = gsonBuilder.create();

在你的情況下,我認為你可以用這種方式解析你的JSON:

DataMessage<YourClass> dataMessage = gson.fromJson(yourJsonObj, DataMessage.class);

另一件事是你可以用這種方式獲得確切的類型

Type collectionType = new TypeToken<DataMessage<T>>() {}.getType();

但是當你反序列化時,你可能會得到一個糟糕的Json ......

最好的方法是使用類而不是T,因此Gson確切知道什么必須序列化/反序列化

Type collectionType = new TypeToken<DataMessage<YourClass>>() {}.getType();

我發現這個為你用GSON反序列化通用類型

假設您要使用JsonReader反序列化DataMessage<T>列表。

public <T> T Gson::fromJson(JsonReader reader, Type typeOfT)

那你有

..
import java.lang.reflect.Type; // make sure you add this import

class DataMessageList<T>
{
    public List<DataMessage<T>> list;

    public DataMessageList ()
    {
        list = null;
    }

    public void readJson (JsonReader reader)
    {
        Type TT = new TypeToken<ArrayList< DataMessage<T> >>(){}.getType();

        this.list = new Gson().fromJson(reader, TT);
    }
}

感謝@Andrea Catania提供的有用幫助,

這里的問題是當我轉換((ParameterizedType) getClass().getGenericSuperclass()).getActualTypeArguments()[0]; Class類型,使用DataMessage<T>類型它無法DataMessage<T>

但是((ParameterizedType) getClass().getGenericSuperclass()).getActualTypeArguments()[0]有類型是Type,所以我不需要把它clazzClass ,我重新鍵入clazz變量到Type (不是Class )並且問題已經解決。

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM