Java使用不同对象类型的数组解析Json(Gson或Jackson等) [英] Java Parse Json with array with different object types (Gson or Jackson or etc.)

查看:163
本文介绍了Java使用不同对象类型的数组解析Json(Gson或Jackson等)的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

  {
response:{
data:{
333:[
{
id:69238,
code:545
},
{
id:69239,
code: 545,
标示:123
}
],
544:[
{
id:69906 ,
code:544,
marked:123
},
{
id:69907,
code:544
}
],
890:[
{
id:69238,
代码:545,
标记:123
},
{
id:69239,
code 545
}
]
}
}
}

我有这个 JSON 数据作为响应并尝试映射。不幸的是,我不能。

第一个原因是对象的索引是可变的。例如,一个索引890和另一个索引是544.

第二个原因是对象中项目的数量是不同的。



当我尝试使用 www.jsonschema2pojo创建java类时。组织。我得到了很多带下划线+整数的类。例如;

  import com.google.gson.annotations.Expose; 
import com.google.gson.annotations.SerializedName;
import org.apache.commons.lang.builder.EqualsBuilder;
import org.apache.commons.lang.builder.HashCodeBuilder;
import org.apache.commons.lang.builder.ToStringBuilder;

public class _544 {

@SerializedName(id)
@Expose
private String id;
@SerializedName(code)
@Expose
private String code;
@SerializedName(标记)
@Expose
私有字符串标记;

public String getId(){
return id;
}

public void setId(String id){
this.id = id;
}

public String getCode(){
return code;
}

public void setCode(String code){
this.code = code;
}

public String getMarked(){
return returned;
}

public void setMarked(String marked){
this.marked = marked;
}

@Override
public String toString(){
return ToStringBuilder.reflectionToString(this);
}

@Override
public int hashCode(){
return new HashCodeBuilder()。append(id).append(code).append(marked)。 toHashCode();
$
$ b @Override
public boolean equals(Object other){
if(other == this){
return true; $(

if((other instanceof _544)== false){
return false;
}
_544 rhs =((_544)other);
返回新的EqualsBuilder()。append(id,rhs.id).append(code,rhs.code).append(marked,rhs.marked).isEquals();
}

}

另一个就是这样

  import com.google.gson.annotations.Expose; 
import com.google.gson.annotations.SerializedName;
import org.apache.commons.lang.builder.EqualsBuilder;
import org.apache.commons.lang.builder.HashCodeBuilder;
import org.apache.commons.lang.builder.ToStringBuilder;

公共类_890 {

@SerializedName(id)
@Expose
私人字符串ID;
@SerializedName(code)
@Expose
private String code;
@SerializedName(标记)
@Expose
私有字符串标记;

public String getId(){
return id;
}

public void setId(String id){
this.id = id;
}

public String getCode(){
return code;
}

public void setCode(String code){
this.code = code;
}

public String getMarked(){
return returned;
}

public void setMarked(String marked){
this.marked = marked;
}

@Override
public String toString(){
return ToStringBuilder.reflectionToString(this);
}

@Override
public int hashCode(){
return new HashCodeBuilder()。append(id).append(code).append(marked)。 toHashCode();
$
$ b @Override
public boolean equals(Object other){
if(other == this){
return true; $(b)b
if((other instanceof _890)== false){
return false;
}
_890 rhs =((_890)other);
返回新的EqualsBuilder()。append(id,rhs.id).append(code,rhs.code).append(marked,rhs.marked).isEquals();
}

}

数字544或890等是动态的

那么我怎样才能用这个动态索引数据与Java进行映射?



感谢您的帮助。

解决方案

您可以使用自定义解串器。下面的例子是使用Gson,但是Jackson可以做同样的事情。

 类CustomDeserializer实现了JsonDeserializer< Response> {

@Override
public Response deserialize(JsonElement jsonElement,Type typeOfElement,JsonDeserializationContext context)throws JsonParseException {
JsonObject data = jsonElement.getAsJsonObject()。get(response) 。.getAsJsonObject()获得( 数据)getAsJsonObject()。
Type listType = new TypeToken< List< Data>>(){} .getType();
地图< String,List< Data>> dataMap = new HashMap< String,List< Data>>(); (Map.Entry< String,JsonElement>条目:data.entrySet()){
List< Data>

。 dataList = context.deserialize(entry.getValue(),listType);

dataMap.put(entry.getKey(),dataList);
}

返回新的响应(dataMap);




$ b $在主类中:

 字符串json =...; 

Gson gson = new GsonBuilder()。registerTypeAdapter(Response.class,new CustomDeserializer())。create();

System.out.println(gson.fromJson(json,Response.class));

回应类:

  class Response {
private Map< String,List< Data>>数据;

public Response(Map< String,List< Data>> data){
this.data = data;


每个数据对象的类别:

  class Data {
private String id;
私人字符串代码;
私人字符串标记;
}

此处的回复将包含每个数据条目的映射及其列表值。 (例如:333 - > Data对象列表),但是您可以更改反序列化器以将键(333)作为Data对象的变量之一并将其分配到for循环中。


 {
   "response": {
     "data": {
       "333": [
         {
           "id": "69238",
           "code": "545"
         },
         {
           "id": "69239",
           "code": "545",
           "marked": "123"
         }
       ],
       "544": [
         {
           "id": "69906",
           "code": "544",
           "marked": "123"
         },
         {
           "id": "69907",
           "code": "544"
         }
       ],
       "890": [
         {
           "id": "69238",
           "code": "545",
           "marked": "123"
         },
         {
           "id": "69239",
           "code": "545"
         }
       ]
     }
   }
 }

I have this JSON data as a response and try to mapping. Unfortunately I can't.

The first reason is index of objects are changeable. For example one index 890 and other one is 544.

The second reason is count of items in object are different.

When I try to create java classes with www.jsonschema2pojo.org. I get lots of classes with underscore + integer. For example;

 import com.google.gson.annotations.Expose;
 import com.google.gson.annotations.SerializedName;
 import org.apache.commons.lang.builder.EqualsBuilder;
 import org.apache.commons.lang.builder.HashCodeBuilder;
 import org.apache.commons.lang.builder.ToStringBuilder;

 public class _544 {

     @SerializedName("id")
     @Expose
     private String id;
     @SerializedName("code")
     @Expose
     private String code;
     @SerializedName("marked")
     @Expose
     private String marked;

     public String getId() {
         return id;
     }

     public void setId(String id) {
         this.id = id;
     }

     public String getCode() {
         return code;
     }

     public void setCode(String code) {
         this.code = code;
     }

     public String getMarked() {
         return marked;
     }

     public void setMarked(String marked) {
         this.marked = marked;
     }

     @Override
     public String toString() {
         return ToStringBuilder.reflectionToString(this);
     }

     @Override
     public int hashCode() {
         return new HashCodeBuilder().append(id).append(code).append(marked).toHashCode();
     }

     @Override
     public boolean equals(Object other) {
         if (other == this) {
             return true;
         }
         if ((other instanceof _544) == false) {
             return false;
         }
         _544 rhs = ((_544) other);
         return new EqualsBuilder().append(id, rhs.id).append(code, rhs.code).append(marked, rhs.marked).isEquals();
     }

 }    

and the other one is like this

import com.google.gson.annotations.Expose;
import com.google.gson.annotations.SerializedName;
import org.apache.commons.lang.builder.EqualsBuilder;
import org.apache.commons.lang.builder.HashCodeBuilder;
import org.apache.commons.lang.builder.ToStringBuilder;

public class _890 {

    @SerializedName("id")
    @Expose
    private String id;
    @SerializedName("code")
    @Expose
    private String code;
    @SerializedName("marked")
    @Expose
    private String marked;

    public String getId() {
        return id;
    }

    public void setId(String id) {
        this.id = id;
    }

    public String getCode() {
        return code;
    }

    public void setCode(String code) {
        this.code = code;
    }

    public String getMarked() {
        return marked;
    }

    public void setMarked(String marked) {
        this.marked = marked;
    }

    @Override
    public String toString() {
        return ToStringBuilder.reflectionToString(this);
    }

    @Override
    public int hashCode() {
        return new HashCodeBuilder().append(id).append(code).append(marked).toHashCode();
    }

    @Override
    public boolean equals(Object other) {
        if (other == this) {
            return true;
        }
        if ((other instanceof _890) == false) {
            return false;
        }
        _890 rhs = ((_890) other);
        return new EqualsBuilder().append(id, rhs.id).append(code, rhs.code).append(marked, rhs.marked).isEquals();
    }

}

The numbers 544 or 890 etc. are dynamic

So how can I do mapping with this dynamic indexed data with Java?

Thanks for help.

解决方案

You can use a custom deserializer. The below example is using Gson, but the same thing can be done with Jackson.

class CustomDeserializer implements JsonDeserializer<Response> {

    @Override
    public Response deserialize(JsonElement jsonElement, Type typeOfElement, JsonDeserializationContext context) throws JsonParseException {
        JsonObject data = jsonElement.getAsJsonObject().get("response").getAsJsonObject().get("data").getAsJsonObject();
        Type listType = new TypeToken<List<Data>>() {}.getType();
        Map<String, List<Data>> dataMap = new HashMap<String, List<Data>>();

        for (Map.Entry<String, JsonElement> entry : data.entrySet()) {
            List<Data> dataList = context.deserialize(entry.getValue(), listType);

            dataMap.put(entry.getKey(), dataList);
        }

        return new Response(dataMap);
    }
}

In the main class:

String json = "...";

Gson gson = new GsonBuilder().registerTypeAdapter(Response.class, new CustomDeserializer()).create();

System.out.println(gson.fromJson(json, Response.class));

Class for the response:

class Response {
    private Map<String, List<Data>> data;

    public Response(Map<String, List<Data>> data) {
        this.data = data;
    }
}

Class for each data object:

class Data {
    private String id;
    private String code;
    private String mark;
}

The response here will have a map of each data entry and a list of its values. (ex: 333 -> list of Data objects), but you can change the deserializer to have the key (333) to be one of the variables of the Data object and assign it in the for loop.

这篇关于Java使用不同对象类型的数组解析Json(Gson或Jackson等)的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆