当前位置: 首页 > 面试题库 >

GSON将键值反序列化为自定义对象

滕英奕
2023-03-14
问题内容

我需要反序列化json,它是日期/长值的数组。这是返回的JSON的示例:

[{"2011-04-30T00:00:00-07:00":100}, {"2011-04-29T00:00:00-07:00":200}]

使用GSON,我可以将其反序列化为List<Map<Date,String>>,但希望能够将其转换为List<MyCustomClass>类似以下内容的方法:

public class MyCustomClass() { 
    Date date;
    Long value;
}

我似乎找不到一种方法来指示GSON将JSON映射的键/值映射到我的自定义类中的日期/值字段。有没有办法做到这一点,还是地图列表是唯一的路线?


问题答案:

您需要编写一个自定义解串器。您还需要使用SimpleDateFormat可以实际解析的时区格式。无论是zZ将匹配-07:00,这是RFC
822时区格式(的一个奇怪的组合-0700)或者“一般的时区”(Mountain Standard TimeMSTGMT-07:00)。另外,您可以坚持使用完全相同的时区格式,并使用JodaTime的DateTimeFormat。

MyCustomClass.java

public class MyCustomClass
{
    Date date;
    Long value;

    public MyCustomClass (Date date, Long value)
    {
        this.date = date;
        this.value = value;
    }

    @Override
    public String toString()
    {
        return "{date: " + date + ", value: " + value + "}";
    }
}

MyCustomDeserializer.java

public class MyCustomDeserializer implements JsonDeserializer<MyCustomClass>
{
    private DateFormat df = new SimpleDateFormat("yyyy-MM-dd'T'HH:mm:ssz");

    @Override
    public MyCustomClass deserialize(JsonElement json, Type typeOfT, JsonDeserializationContext ctx) throws JsonParseException
    {
        JsonObject obj = json.getAsJsonObject();
        Entry<String, JsonElement> entry = obj.entrySet().iterator().next();
        if (entry == null) return null;
        Date date;
        try
        {
            date = df.parse(entry.getKey());
        }
        catch (ParseException e)
        {
            e.printStackTrace();
            date = null;
        }
        Long value = entry.getValue().getAsLong();
        return new MyCustomClass(date, value);
    }
}

GsonTest.java

public class GsonTest
{
    public static void main(String[] args)
    {
        // Note the time zone format tweak (removed the ':')
        String json = "[{\"2011-04-30T00:00:00-0700\":100}, {\"2011-04-29T00:00:00-0700\":200}]";

        Gson gson =
            new GsonBuilder()
            .registerTypeAdapter(MyCustomClass.class, new MyCustomDeserializer())
            .create();
        Type collectionType = new TypeToken<Collection<MyCustomClass>>(){}.getType();
        Collection<MyCustomClass> myCustomClasses = gson.fromJson(json, collectionType);
        System.out.println(myCustomClasses);
    }
}

上面的所有代码都在Github上,可以随时克隆(尽管您还将获得用于回答其他问题的代码)。



 类似资料:
  • 问题内容: 确定,所以我编辑了问题,因为它不够清楚。 编辑2 :更新了JSON文件。 我在Android应用程序中使用GSON,我需要解析来自服务器的JSON文件,这些文件有点太复杂了。我不想让我的对象结构太沉重,所以我想简化内容: 所以我的对象的结构将不是JSON文件的结构。 例如,如果在JSON中,我有以下内容: 我不想保留我当前的对象结构,即一个对象,其中包含一个和一个“总计”。但是我只想将

  • 我有一个JestClient(elasticsearch)响应,我试图将其反序列化为一个对象。该对象包含两个DateTime字段,而在响应中,它们是字符串,因此我得到: 所以,我创建了一个自定义反序列化器来解决这个问题…然而,无论我做什么,我总是得到同样的错误。不知何故它没有注册使用它? 最后,我试图解析JestClient响应的代码: 无论我尝试什么,我总是得到上面的错误,我甚至不确定在这一点上

  • 我使用NewtonSoft.json来反序列化这个json

  • 我的类有一个自定义反序列化程序,如下所示: 这是我在创建Gson对象时注册反序列化程序的方式: 最后,像这样解析我的JSON: 在我的方法中,的值如下然后它作为加载到数据映射中。我想看看是否有任何方法可以让映射的所有值都是小写的,所以它应该像那样自动存储在数据映射中,而不是像这样? 有没有办法在Gson中自动实现这一点? 更新: 以下是我的JSON内容:

  • 问题内容: 我在使用Gson解析JSON响应时遇到问题。 JSON字串: 我有这两个课程: 但是当使用Gson解析这个时我有一个异常。我知道这是因为响应数组的第一个元素不是对象,而是整数。 所以问题是,我能以某种方式解决它吗? 问题答案: 您必须编写一个 自定义反序列化器 。我会做这样的事情: 首先,您需要包括一个新的类,而不是已有的两个类: 然后,您需要一个自定义解串器,类似于以下内容: 然后,

  • 我有下面的JSON,我正试图使用Jackson API反序列化它 我基本上需要一个附件类,它有一个AttachmentFile对象列表,如下所示: 如何使用自定义反序列化器实现这一点? 谢谢