繁体   English   中英

JSON多态反序列化Java

[英]JSON polymorphic deserialization java

我有一个像JSON这样的文件系统结构,如下所示:

{
    "name": "rootf",
    "type": "system",
    "path": "Parsing/rootf",
    "children": [{
        "name": "f1",
        "type": "folder",
        "path": "Parsing/rootf/f1",
        "children": [{
            "name": "subf1",
            "type": "folder",
            "path": "Parsing/rootf/f1/subf1",
            "children": [{
                "name": "text1.txt",
                "type": "file",
                "path": "Parsing/rootf/folder1/subf1/text1.txt",
                "children": ["a", "b", "c"]
            }]
        }, {
            "name": "subf2",
            "type": "folder",
            "path": "Parsing/rootf/f1/subf2",
            "children": []
        }, {
            "name": "text2.txt",
            "type": "file",
            "path": "TParsing/rootf/f1/text2.txt",
            "children": ["d", "e", "f"]
        }]
    }, {
        "name": "text1.txt",
        "type": "file",
        "path": "Parsing/rootd/text1.txt",
        "children": ["aa", "bb"]
    }],
    "_id": "5ce47292d866fc2f40037a56"
}

可以看出, system类型(表示根文件夹)和文件夹类型(表示根文件folder子文件夹)的子级可以包含其他文件夹和/或文件。 文件类型的子项包含文件的内容。 我有一个抽象类Component

public abstract class Component implements IComponent{

    private String name;
    private String type;
    private String path;
    public abstract <T extends IComponent> ISystem<T> getSystem();

}

和另一个抽象类SystemAdapter

public abstract class SystemAdapter<T extends IComponent>
        implements ISystem<T> {

    private LinkedHashSet<ComponentType> components;
    protected abstract Set<ComponentType> components();
    public Set<ComponentType> getComponents() {
        return components;
    }

我有3个具体的类,它们扩展了两个抽象类:

public class System extends SystemAdapter{
    public transient Set<ComponentWrapper> components;
    private List<????> children;
    private String name;
    private String id;
    private String type;
    private String path;
public class Folder extends Component{

    public List<????> children = new ArrayList<>();
    private String name;
    private String type;
    private String path;
public class File extends Component{

    public List<String> children = new ArrayList<>();
    private String name;
    private String type;
    private String path;

我一直在努力将必须的JSON映射到这三个类。 由于children可以是Folder类型或File类型,我该如何映射? 我的目标是将system类型(即根文件夹) System.javaSystem.java ,将folder类型Folder.javaFolder.java ,并将JSON中的file类型File.javaFile.java

第二部分是能够获取特定系统的components ,并且对于特定system获取所有components的集合(即,对于特定的根文件夹,获取其所有文件和子文件夹)。

我看到了一些与JSON多态反序列化有关的问题,但是我不确定这在这里是否适合。 任何指导都将真正有帮助。

这取决于您在Java中使用的库,但是如果您使用的是Jackson ,则可以使用其中的type值对抽象类Component反序列化。

@JsonTypeInfo(use = JsonTypeInfo.Id.NAME, property = "type")
@JsonSubTypes({
        @JsonSubTypes.Type(value = Folder.class, name = "folder")
        @JsonSubTypes.Type(value = File.class, name = "file")
})
public abstract class Component implements IComponent{
    //...
}

基本上,这将告诉杰克逊在读取type字段中的Folder时鼓励Folder folder ,对于file字段也是如此。

作为System File FolderComponent所有类都具有相同的属性

private String name;
private String type;
private String path;

您可以在“ Component中使这些字段受保护,以便所有“ System File Folder都可以继承它们。 由于系统类具有额外的ID字段,因此您只能在System类中添加id

所以最后您的课程可能喜欢这些:

public abstract class Component implements IComponent{

    protected String name;
    protected String type;
    protected String path;
    public abstract <T extends IComponent> ISystem<T> getSystem();
    ....

public class Children extends Component{
    public List<Children> children = new ArrayList<>();
    ...

public class System extends Children implements SystemAdapter{
    public transient Set<ComponentWrapper> components;
    private String id;
    ....

取决于您使用的是哪个JSON引擎,但是使用Jackson可以在父类上指定JsonTypeInfo批注。

https://fasterxml.github.io/jackson-annotations/javadoc/2.4/com/fasterxml/jackson/annotation/JsonTypeInfo.html

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM