使用 GSON 将 JSON 样式属性名称转换为 Java CamelCase 名称
声明:本页面是StackOverFlow热门问题的中英对照翻译,遵循CC BY-SA 4.0协议,如果您需要使用它,必须同样遵循CC BY-SA许可,注明原文地址和作者信息,同时你必须将它归于原作者(不是我):StackOverFlow
原文地址: http://stackoverflow.com/questions/2370745/
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
Convert JSON style properties names to Java CamelCase names with GSON
提问by Janusz
I'm using GSONto convert JSON data I get to a Java object. It works pretty well in all my tests. The problem is that our real objects have some properties named like is_online. GSON only maps them if they are named totally equal, it would be nice to have GSON convert the names to Java camel case isOnline.
我正在使用GSON将我得到的 JSON 数据转换为 Java 对象。它在我的所有测试中都运行良好。问题是我们的真实对象有一些名为 is_online 的属性。GSON 仅在它们的名称完全相同时才映射它们,让 GSON 将名称转换为 Java 驼峰式 isOnline 会很好。
It seems this is possible while creating the JSON data, camel case is converted to underscore separated words in JSON. But I can't find a way to specify this the other way round.
在创建 JSON 数据时,这似乎是可能的,驼峰式大小写在 JSON 中转换为下划线分隔的单词。但我找不到另一种方式来指定这一点。
回答by Jherico
Bear in mind your example is an edge case. If you have a property 'foo' its getter should be named 'getFoo', and if you have a property named 'foo_bar' its getter should be named 'getFooBar', however, in your example you're mapping a boolean and booleans have special case naming conventions in java. A primitive boolean property named online should have a getter named 'isOnline', NOT 'getOnline' or even worse, 'getIsOnline'. A boolean wrapper object (i.e. Boolean) should not follow this special case and a property named 'online' should have a getter named 'getOnline'.
请记住,您的示例是边缘情况。如果你有一个属性“foo”,它的getter应该被命名为“getFoo”,如果你有一个名为“foo_bar”的属性,它的getter应该被命名为“getFooBar”,但是,在你的例子中,你正在映射一个布尔值,布尔值有java中的特殊情况命名约定。一个名为 online 的原始布尔属性应该有一个名为 'isOnline' 的 getter,而不是 'getOnline' 或更糟的是,'getIsOnline'。布尔包装对象(即布尔值)不应遵循这种特殊情况,并且名为“online”的属性应具有名为“getOnline”的 getter。
Hence, having boolean properties with 'is' in the name is an edge case, where you'll want to strip out this particular prefix during your conversion. In the reverse direction, your code may want to inspect the json object for both a raw property name as well as a 'is_XXX' version.
因此,名称中带有 'is' 的布尔属性是一种边缘情况,您需要在转换过程中去掉这个特定的前缀。相反,您的代码可能需要检查 json 对象的原始属性名称和“is_XXX”版本。
回答by MBCook
I think what you want is here. Using annotations you can tell GSON that the mySuperCoolField is actually called this_field_is_fun in the JSON and it will unpack it correctly. At least I think it works for deserialization too.
我想你想要的就在这里。使用注释,您可以告诉 GSON mySuperCoolField 实际上在 JSON 中称为 this_field_is_fun 并且它会正确解压缩它。至少我认为它也适用于反序列化。
If that doesn't work, you can use custom JsonSerializer/JsonDeserializers, which work great, but you have to update them for changes in your class (like when you add a field). You lose the auto-magic.
如果这不起作用,您可以使用自定义 JsonSerializer/JsonDeserializers,它们工作得很好,但您必须更新它们以进行类中的更改(例如添加字段时)。你失去了自动魔法。
The easiest thing to do (which would be ugly, but very clean and simple if the first suggestion doesn't work) would be to simply name the field in a way to make GSON happy, and add extra accessor methods with the names you like, e.g.
最简单的方法(如果第一个建议不起作用,这将是丑陋的,但非常干净和简单)是简单地以一种让 GSON 满意的方式命名该字段,并使用您喜欢的名称添加额外的访问器方法,例如
public boolean isXXX() {return this.is_XXX;}
回答by Hampei
I have found the following setting works perfect when reading json with underscored attributes and using camelcasing in my models.
我发现以下设置在读取带有下划线属性的 json 并在我的模型中使用驼峰格式时非常有效。
Gson gson = new GsonBuilder()
.setFieldNamingPolicy(FieldNamingPolicy.LOWER_CASE_WITH_UNDERSCORES)
.create()
回答by saschoar
You can use the SerializedName
annotation:
您可以使用SerializedName
注释:
@SerializedName("field_name_in_json")
private final String fieldNameInJava;
Note: When you have set a FieldNamingPolicy
already, SerializedName
will overwrite its settings for that specific field (quite handy for special cases).
注意:当您已经设置了 a 时FieldNamingPolicy
,SerializedName
将覆盖该特定字段的设置(对于特殊情况非常方便)。