使用 gson 将 json 解析为 java 对象的问题

声明:本页面是StackOverFlow热门问题的中英对照翻译,遵循CC BY-SA 4.0协议,如果您需要使用它,必须同样遵循CC BY-SA许可,注明原文地址和作者信息,同时你必须将它归于原作者(不是我):StackOverFlow 原文地址: http://stackoverflow.com/questions/13873887/
Warning: these are provided under cc-by-sa 4.0 license. You are free to use/share it, But you must attribute it to the original authors (not me): StackOverFlow

提示:将鼠标放在中文语句上可以显示对应的英文。显示中英文
时间:2020-10-31 14:16:02  来源:igfitidea点击:

Issue with parse json to java object using gson

javagwtgson

提问by bNd

I want to parse json data into java object using google-gson.

我想使用google-gson将 json 数据解析为 java 对象。

Here is an example of the data I want to parse:

这是我要解析的数据的示例:

  {"isBean":{"userName":"test","password":"password112"}}

IsBean.java

IsBean.java

public interface IsBean extends Serializable,IsSerializable{

    long getId();

}

User.java

用户.java

public class User implements IsBean,IsSerializable,Serializable {

    String userName;
    String password;

    public String getUserName() {
        return userName;
    }
    public void setUserName(String userName) {
        this.userName = userName;
    }
    public String getPassword() {
        return password;
    }
    public void setPassword(String password) {
        this.password = password;
    }
    @Override
    public long getId() {
        return 0;
    }


}

RequestObj.java

请求对象

public class RequestObj implements IsBean, Serializable,IsSerializable{

    IsBean  isBean;
    @Override
    public long getId() {
        return 0;
    }
     public IsBean getIsBean() {
        return isBean;
    }
    public void setIsBean(IsBean isBean) {
        this.isBean = isBean;
    }
}

Test.java

测试.java

public class Test {

    public static void main(String[] args) {
        Gson gson = new Gson();
        User user=new User();
        user.setPassword("password112");
        user.setUserName("test");
        RequestObj requestObj=new RequestObj();
        requestObj.setIsBean(user);
        String jsonStr=gson.toJson(requestObj);
        System.out.println("jsonStr--->"+jsonStr);
        try{
            RequestObj request=gson.fromJson(jsonStr, RequestObj.class);
        }catch (Exception e) {
        e.printStackTrace();
        }
    }
}

Error:

错误:

java.lang.RuntimeException: Unable to invoke no-args constructor for interface com.test.gson.shared.IsBean. Register an InstanceCreator with Gson for this type may fix this problem.
    at com.google.gson.internal.ConstructorConstructor.construct(ConstructorConstructor.java:167)
    at com.google.gson.internal.bind.ReflectiveTypeAdapterFactory$Adapter.read(ReflectiveTypeAdapterFactory.java:162)
    at com.google.gson.internal.bind.ReflectiveTypeAdapterFactory.read(ReflectiveTypeAdapterFactory.java:93)
    at com.google.gson.internal.bind.ReflectiveTypeAdapterFactory$Adapter.read(ReflectiveTypeAdapterFactory.java:172)
    at com.google.gson.Gson.fromJson(Gson.java:795)
    at com.google.gson.Gson.fromJson(Gson.java:761)
    at com.google.gson.Gson.fromJson(Gson.java:710)
    at com.google.gson.Gson.fromJson(Gson.java:682)
    at com.test.gson.server.Test.main(Test.java:18)
Caused by: java.lang.reflect.InvocationTargetException
    at sun.reflect.NativeMethodAccessorImpl.invoke0(Native Method)
    at sun.reflect.NativeMethodAccessorImpl.invoke(NativeMethodAccessorImpl.java:39)
    at sun.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:25)
    at java.lang.reflect.Method.invoke(Method.java:597)
    at com.google.gson.internal.UnsafeAllocator.newInstance(UnsafeAllocator.java:48)
    at com.google.gson.internal.ConstructorConstructor.construct(ConstructorConstructor.java:164)
    ... 8 more
Caused by: java.lang.InstantiationException: com.test.gson.shared.IsBean
    at sun.misc.Unsafe.allocateInstance(Native Method)
    ... 14 more

采纳答案by NawaMan

Without seeing the code of CommunicationObject, I can't say for sure BUT I am guessing with confidence that the class has a field of type IsBeanin which you use it to hold the User. If so, the problem is that GSON scans fields of the object objof the class CommunicationObjectand based on the field definition, the value of the field (which is typed IsBean) will have to be created BUT since the type is an interface, it can't instance object for that field.

没有看到的代码CommunicationObject,我不能肯定地说,但我有信心,有类类型的字段猜测IsBean中,你用它来保存User。如果是这样,问题是 GSON 扫描obj类的对象的字段,CommunicationObject并根据字段定义,IsBean必须创建字段的值(类型),但由于类型是接口,因此不能该字段的实例对象。

Another words, as JSON field does not specifies the object type, GSON must relies on the defined type of the field to create the instance for the field value which can't be done if the type is an interface.

换句话说,由于JSON字段没有指定对象类型,所以GSON必须依赖于定义的字段类型来为字段值创建实例,如果类型是接口,则无法做到这一点。

So, consider changing the type of that field if that make sense to you. OR look into creating InstanceCreatorof IsBean(doute that it is logically possible).

因此,如果对您有意义,请考虑更改该字段的类型。或可考虑建立InstanceCreatorIsBean(doute,这在逻辑上是可能的)。

See also: Deserializing an abstract class in Gson

另请参阅:反序列化 Gson 中的抽象类

Hope this helps.

希望这可以帮助。

回答by bNd

The problem is solved With the help of Stackoverflow Answer.

问题在 Stackoverflow Answer的帮助下得到解决。

Create gson object:

创建 gson 对象:

Gson gson = new GsonBuilder().registerTypeAdapter(IsBean.class, new InterfaceAdapter<IsBean>()).create();