Warning: file_get_contents(/data/phpspider/zhask/data//catemap/9/java/399.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181

Warning: file_get_contents(/data/phpspider/zhask/data//catemap/4/json/15.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
Java 使用Jackson的部分JSON序列化/反序列化_Java_Json_Jackson - Fatal编程技术网

Java 使用Jackson的部分JSON序列化/反序列化

Java 使用Jackson的部分JSON序列化/反序列化,java,json,jackson,Java,Json,Jackson,我有一个暂时无法解决的问题。 让我们想象一个非常简单的Java类 class Foo { public String bar; public String baz; } 我如何才能实现某些JSON请求的反序列化和后续序列化操作对于部分JSON对象来说实际上是不可变的。所以如果我不相信 { "bar": "some value", "baz": null } 输入Foo实例,然后将其序列化回JSON,我得到 { "bar": "some value"

我有一个暂时无法解决的问题。 让我们想象一个非常简单的Java类

class Foo {
     public String bar;
     public String baz;
}
我如何才能实现某些JSON请求的反序列化和后续序列化操作对于部分JSON对象来说实际上是不可变的。所以如果我不相信

{
    "bar": "some value",
    "baz": null
}
输入Foo实例,然后将其序列化回JSON,我得到

{
    "bar": "some value",
    "baz": null
}
如果我不使用“baz”取消序列化部分JSON

我再次得到一个不带“baz”的部分JSON


除非存储关于原始JSON对象中存在哪些字段的信息,否则这是不可能的。为此,您可以在
Foo
周围使用一个包装器,其中包含
Foo
和此附加信息。下面是一个例子

注意:这是伪代码。方法和类名部分来自Gson库,部分是我在飞行中发明的,但你明白了。我认为用Jackson的课程来翻译这个应该不难

class DeserializedFoo {

    private Foo foo;
    private Set<String> includedFields = new HashSet<>();

    private DeserializedFoo(){

    }

    public static class DeSerializer implements JsonDeserializer<DeserializedFoo> {
        @Override
        public DeserializedFoo deserialize(JsonElement je) {
            DeserializedFoo dsFoo = new DeserializedFoo();
            dsFoo.foo = parse(je);
            for(JsonElement prop : je.elements()){
                includedFields.add(prop.getName());
            }
            return dsFoo;
        }
    }

    public static class Serializer implements JsonSerializer<DeserializedFoo> {
        @Override
        public JsonElement serialize(DeserializedFoo dsFoo) {
            JsonElement jsonFoo = serialize(dsFoo.foo);

            // Leave only fields that were present in the JSON 
            // element from which this was deserialized.
            Iterable it = jsonFoo.elements().iterable();
            while(it.hasNext()){
                JsonElement prop = it.next();
                if(!includedFields.contains(prop.getName()){
                    it.remove();
                }
            }
            return jsonFoo;
        }
    }   
}
类反序列化DFOO{
私人富福;
private Set includedFields=new HashSet();
私有反序列化dfoo(){
}
公共静态类反序列化器实现JsonDeserializer{
@凌驾
公共反序列化OO反序列化(JsonElement je){
DeserializedFoo dsFoo=新的DeserializedFoo();
dsFoo.foo=parse(je);
对于(JsonElement prop:je.elements()){
includedFields.add(prop.getName());
}
返回dsFoo;
}
}
公共静态类序列化程序实现JsonSerializer{
@凌驾
公共JsonElement序列化(反序列化DFOO dsFoo){
JsonElement-jsonFoo=serialize(dsFoo.foo);
//只保留JSON中存在的字段
//从中反序列化此的元素。
Iterable it=jsonFoo.elements().Iterable();
while(it.hasNext()){
JsonElement prop=it.next();
如果(!includedFields.contains(prop.getName()){
it.remove();
}
}
返回jsonFoo;
}
}   
}

当然,您可以使用继承而不是包装器,例如,通过定义
类DeserilizedFoo扩展Foo
并添加
includedFields
字段。每种方法都有其优点和缺点。由您决定哪种方法最适合您的情况。

您可以使用和注释您的类 将
baz
属性的默认值设置为一个魔术字符串,这将指示该值不应出现在JSON中

以下是一个例子:

public class JacksonIncludeNull {

    final static String JSON1 = "{\n" +
            "    \"bar\": \"some value\",\n" +
            "    \"baz\": null\n" +
            "}";

    final static String JSON2 = "{\n" +
            "    \"bar\": \"some value\"\n" +
            "}";

    @JsonInclude(JsonInclude.Include.NON_DEFAULT)
    static class Foo {
        public String bar;
        public String baz = "##default";

        @Override
        public String toString() {
            return "Foo{" +
                    "bar='" + bar + '\'' +
                    ", baz='" + baz + '\'' +
                    '}';
        }
    }

    public static void main(String[] args) throws IOException {
        final ObjectMapper mapper = new ObjectMapper();
        mapper.registerModule(new GuavaModule());
        final Foo foo1 = mapper.readValue(JSON1, Foo.class);
        System.out.println(JSON1);
        System.out.println("Object: " + foo1);
        System.out.println("Serialize: " + mapper.writeValueAsString(foo1));

        System.out.println();

        final Foo foo2 = mapper.readValue(JSON2, Foo.class);
        System.out.println(JSON2);
        System.out.println("Object: " + foo2);
        System.out.println("Serialize: " + mapper.writeValueAsString(foo2));
    }
}
输出:

{
    "bar": "some value",
    "baz": null
}
Object: Foo{bar='some value', baz='null'}
Serialize: {"bar":"some value","baz":null}

{
    "bar": "some value"
}
Object: Foo{bar='some value', baz='##default'}
Serialize: {"bar":"some value"}
public class JacksonIncludeNull {

    final static String JSON1 = "{\n" +
            "    \"bar\": \"some value\",\n" +
            "    \"baz\": null\n" +
            "}";

    final static String JSON2 = "{\n" +
            "    \"bar\": \"some value\"\n" +
            "}";

    @JsonInclude(JsonInclude.Include.NON_DEFAULT)
    static class Foo {
        public String bar;
        public String baz = "##default";

        @Override
        public String toString() {
            return "Foo{" +
                    "bar='" + bar + '\'' +
                    ", baz='" + baz + '\'' +
                    '}';
        }
    }

    public static void main(String[] args) throws IOException {
        final ObjectMapper mapper = new ObjectMapper();
        mapper.registerModule(new GuavaModule());
        final Foo foo1 = mapper.readValue(JSON1, Foo.class);
        System.out.println(JSON1);
        System.out.println("Object: " + foo1);
        System.out.println("Serialize: " + mapper.writeValueAsString(foo1));

        System.out.println();

        final Foo foo2 = mapper.readValue(JSON2, Foo.class);
        System.out.println(JSON2);
        System.out.println("Object: " + foo2);
        System.out.println("Serialize: " + mapper.writeValueAsString(foo2));
    }
}
{
    "bar": "some value",
    "baz": null
}
Object: Foo{bar='some value', baz='null'}
Serialize: {"bar":"some value","baz":null}

{
    "bar": "some value"
}
Object: Foo{bar='some value', baz='##default'}
Serialize: {"bar":"some value"}