我有一个复杂/嵌套的json。我的json文件由两个等效的Java对象组成。一个是Complex_Expression
,另一个是Simple_Expression
。
Complex_Expression
的格式如下:
{
"SomeOpearator":0,
"ASpecificKey":1, //the value 1 is fixed for complex expression.
"Expressions":[ ] //array of one or more expressions
}
Simple Expression
的格式如下:
{
"Operand":"Some String Value",
"ASpecificKey":0, //the value 0 is fixed for simple expressions.
"SomeComparisionOpearator":1, // enums which associates int to different comparison operators.
"Value":["String1"] //this is an array of strings.
}
Expressions
可以具有Complex_Expression
和/或Simple_Expression
。 json文件始终从Complex_Expression
开始。我必须反序列化此JSON文件。我的最终目标是使用Complex_Expression
和Simple_Expression
对象以及这些类中的某些逻辑来创建表达式。我不介意使用jackson
或gson
或其他依赖项。
到目前为止,我已经创建了一个名为Expression
的基类。 Complex_Expression
和Simple_Expression
都继承了此类。然后,我开始写Custom Json Deserializer
。但是在自定义解串器中,我陷入了困境,我不知道该如何进行。请帮我。我的Simple_Expression
类看起来像这样,而Complex_Expression
类也有些相似。
public class Simple_Expression extends Expression
{
@JsonProperty("Operand") //use jackson deserializer for this class.
public String Operand;
@JsonProperty("SomeComparisionOpearator")
public SomeComparisionOpearator someCompareOperator;
@JsonProperty("Value")
public Object value;
public Simple_Expression()
{
super(ASpecificKey.Simple); //Simple corresponds to 0
}
}
更新
有关我的输入和输出的更多描述。输入指定了这样的JSON字符串:
{
"SomeOpearator": 0,
"ASpecificKey": 1,
"Expressions": [
{
"SomeOpearator": 1,
"ASpecificKey": 1,
"Expressions": [
{
"Operand": "People",
"ASpecificKey": 0,
"SomeComparisionOpearator": 14,
"Value": [
"Rich"
]
}
]
},
{
"SomeOpearator": 1,
"ASpecificKey": 1,
"Expressions": [
{
"Operand": "Grade",
"ASpecificKey": 0,
"SomeComparisionOpearator": 2,
"Value": [
"Grade A"
]
}
]
}
]
}
假设杰克逊解串器,我应该能够执行以下操作:
ObjectMapper mapper = new ObjectMapper();
Expression myExpressionObject = mapper.convertValue(jsonString, Expression.class);
它应该给我反序列化的对象到myExpressionObject中,该对象将由表达式列表(Arraylist或Array,没问题)组成。
答案 0 :(得分:1)
使用Gson Extras RuntimeTypeAdapterFactory
会很容易,因为您拥有字段ASpecificKey
可用作类型区分符。有关用法,请参见this。如果您已经包含Gson,则可以仅将源代码复制到项目中。
我自由地修复了您的Java命名约定,因此类实际上看起来像(而且您的JSON应该被修正为正确的约定):
@Getter @Setter
public class Expression {
private int aSpecificKey;
}
@Getter @Setter
public class SimpleExpression extends Expression {
public SimpleExpression() {
setASpecificKey(0);
}
private String operand;
private int someComparisonOperator;
private String[] values;
}
@Getter @Setter
public class ComplexExpression extends Expression {
public ComplexExpression() {
setASpecificKey(1);
}
private String someOperator;
private Expression[] expressions;
}
针对这种DTO,您只需实例化特定的RuntimeTypeAdapterFactory
:
final RuntimeTypeAdapterFactory<Expression> expressionTypeFactory =
RuntimeTypeAdapterFactory
.of(Expression.class, "aSpecificKey")
.registerSubtype(SimpleExpression.class, "0")
.registerSubtype(ComplexExpression.class, "1")
然后反序列化将是:
Expression e = getGson(expressionTypeFactory)
.fromJson(getPackageResourceReader(YOUR_NOTATION_FIXED_JSON),
Expression.class);
请注意,Gson默认情况下不会反序列化鉴别符aSpecificKey
的类型,这就是为什么有默认构造函数对此进行设置的原因。如果不需要它,则可以删除默认构造函数。