当键不是原始值时反序列化泛型哈希图
我想使用泛型对哈希图进行 gson 和 de-gson。
当我的密钥是字符串时我可以成功完成此操作,但如果它是
对象。
我这里有两个代码部分。第一个不起作用,第二个不起作用
做。
// doesnt work works
try {
TradableBean tradable = new TradableBean("Tradable");
PositionBean position = new PositionBean(tradable);
Map<TradableBean, PositionBean> map1 = new HashMap<TradableBean, PositionBean>();
map1.put(tradable, position);
String json1 = gson.toJson(map1);
Map<TradableBean, PositionBean> map2 = gson.fromJson(json1, new TypeToken<Map<TradableBean, PositionBean>>(){}.getType());
System.out.println(map2);
} catch (Exception e) {
System.out.println("failed");
}
现在是工作部分 -
// works - with string
try {
String tradable = new String("Tradable");
PositionBean position = new PositionBean(new TradableBean("Tradable"));
Map<String, PositionBean> map1 = new HashMap<String,PositionBean>();
map1.put(tradable, position);
String json1 = gson.toJson(map1);
Map<String, PositionBean> map2 = gson.fromJson(json1, new TypeToken<Map<String, PositionBean>>() {}.getType());
System.out.println(map2);
} catch (Exception e) {
System.out.println("failed");
}
在 TradableBean 中我有:
@Override public int hashCode() {
return getId();}
@Override public boolean equals(Object obj) {
boolean equals = false;
if (obj instanceof AccountBean){
TradableBean tradable_p = (TradableBean)obj;
if (getId()==tradable_p.getId()){
equals = true;
}
}
return equals;
}
例外:
com.google.gson.JsonParseException:期望找到对象: "TradableBean{id=0, tradableName='可交易', MoneyMultiplier=1, 过期日期=空}” 在 com.google.gson.JsonObjectDeserializationVisitor.visitFieldUsingCustomHandler(JsonObjectDeserializationVisitor.java: 100) 在 com.google.gson.ObjectNavigator.navigateClassFields(ObjectNavigator.java: 150) 在 com.google.gson.ObjectNavigator.accept(ObjectNavigator.java:123) 在 com.google.gson.JsonDeserializationContextDefault.fromJsonPrimitive(JsonDeserializationContextDefault.java: 84) 在 com.google.gson.JsonDeserializationContextDefault.deserialize(JsonDeserializationContextDefault.java: 53) 在 com.google.gson.DefaultTypeAdapters $MapTypeAdapter.deserialize(DefaultTypeAdapters.java:531) 在 com.google.gson.DefaultTypeAdapters $MapTypeAdapter.deserialize(DefaultTypeAdapters.java:498) 在 com.google.gson.JsonDeserializerExceptionWrapper.deserialize(JsonDeserializerExceptionWrapper.java: 50)
如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。
绑定邮箱获取回复消息
由于您还没有绑定你的真实邮箱,如果其他用户或者作者回复了您的评论,将不能在第一时间通知您!
发布评论
评论(2)
丹的回答是正确的。
您遇到的 Gson 限制涉及它当前如何序列化映射键:通过调用
toString()
。来自MapTypeAdapter
:MapTypeAdapter
文档中也描述了此行为。如果您坚持使用自定义类型作为映射键,那么我可以告诉您,您将必须编写一个自定义序列化器和/或自定义反序列化器和/或生成的
toString()
易于反序列化的字符串表示形式。另外,请查看 MapAsArrayTypeAdapter 是一种方法。 (它可以通过调用
GsonBuilder.enableComplexMapKeySerialization()
来使用,而不是通过文档描述的直接实例化(因为它当前不是公共类)。我没有测试它来查看它的实现是否有效,但看起来很有希望。)Dan's answer is on the right track.
The Gson limitation you're bumping up against concerns how it currently serializes map keys: by calling
toString()
. FromMapTypeAdapter
:This behavior is also described in the
MapTypeAdapter
documentation.If you insist on using custom types as map keys, then as best I can tell you're going to have to write a custom serializer and/or a custom deserializer and/or a
toString()
that generates a string representation that's easy to deserialize.Also, take a look at MapAsArrayTypeAdapter for one approach. (It's usable with a call to
GsonBuilder.enableComplexMapKeySerialization()
, not through direct instantiation as the docs describe (because it's currently not a public class). I didn't test it to see if its implementation works, but it looks promising.)我认为您需要编写自己的 自定义序列化器。
更新: 例外是:
前置字符串“TradableBean”似乎是由使用某种
toString()
的序列化编写的。反序列化需要一个{id=0,... }
形式的对象I think you need to write your own custom serializator.
Update: the tell-tale is the exception:
The prepending string "TradableBean" seems to be written by a serialization that uses some sort of
toString()
. the Deserialization expected an object of the form{id=0,... }