Java 乔尔树结构

Java 乔尔树结构,java,tree,java-stream,inner-join,jool-library,Java,Tree,Java Stream,Inner Join,Jool Library,我有一个文档集合:列表文档。该文件的结构如下所示: id、级别、aoguid、parentguid、formalname、currstatus 。此结构允许您创建地址树结构。也就是说:国家一级、城市二级、街道三级,依此类推到七级。有些级别可能是,也可能不是。我的任务是:形成包含完整地址和组成完整地址的部分数组的json { "full Address": "Country city street house", "parts": [ { "id": 1,

我有一个文档集合:列表文档。该文件的结构如下所示:

id、级别、aoguid、parentguid、formalname、currstatus

。此结构允许您创建地址树结构。也就是说:国家一级、城市二级、街道三级,依此类推到七级。有些级别可能是,也可能不是。我的任务是:形成包含完整地址和组成完整地址的部分数组的json

{
  "full Address": "Country city street house",
  "parts": [
    {
      "id": 1,
      "aoguid": 1,
      "parentguid": 0,
      "formalname": "country",
      "currstatus": 0
    },
    {
      "id": 2,
      "aoguid": 2,
      "parentguid": 1,
      "formalname": "city",
      "currstatus": 0
    },
    {
      "id": 3,
      "aoguid": 3,
      "parentguid": 2,
      "formalname": "street",
      "currstatus": 0
    },
    {
      "id": 4,
      "aoguid": 4,
      "parentguid": 3,
      "formalname": "house",
      "currstatus": 0
    }
  ]
}
由于项目使用的是mongoDb,而不是关系数据库,因此任务变得复杂。但是我发现,使用JOOL框架,您可以像SQL一样进行JAVA查询。我写了这段代码:

Seq<Document> seq1 = Seq.seq(listDocs).filter(
        it -> isNull(it.get("currstatus")) || "0".equals(it.get("currstatus"))
);
Seq<Document> seq2 = seq1;
Seq<Document> seq3 = seq1;
Seq<Document> seq4 = seq1;
Seq<Document> seq5 = seq1;
Seq<Document> seq6 = seq1;
Seq<Document> seq7 = seq1;

seq1
        .leftOuterJoin(seq2, (l1, l2) -> Objects.equals(l1.get("aoguid"), l2.get("parentguid")))
        .leftOuterJoin(seq3, (l2, l3) -> Objects.equals(l2.v2.get("aoguid"), l3.get("parentguid")))
        .leftOuterJoin(seq4, (l3, l4) -> Objects.equals(l3.v3.get("aoguid"), l4.get("parentguid")))
        .leftOuterJoin(seq5, (l4, l5) -> Objects.equals(l4.v4.get("aoguid"), l5.get("parentguid")))
        .leftOuterJoin(seq6, (l5, l6) -> Objects.equals(l5.v5.get("aoguid"), l6.get("parentguid")))
        .leftOuterJoin(seq7, (l6, l7) -> Objects.equals(l6.v6.get("aoguid"), l7.get("parentguid")))
        .parallel()
        .forEach(it -> {
            System.out.println("Some actions....");
        });
Seq seq1=Seq.Seq(listDocs).filter(
it->isNull(it.get(“currstatus”))| |“0”。等于(it.get(“currstatus”))
);
Seq seq2=seq1;
Seq seq3=seq1;
Seq seq4=seq1;
Seq seq5=seq1;
Seq seq6=seq1;
Seq Seq 7=Seq 1;
序号1
.leftOuterJoin(seq2,(l1,l2)->Objects.equals(l1.get(“aoguid”)、l2.get(“parentguid”))
.leftOuterJoin(seq3,(l2,l3)->Objects.equals(l2.v2.get(“aoguid”)、l3.get(“parentguid”))
.leftOuterJoin(seq4,(l3,l4)->Objects.equals(l3.v3.get(“aoguid”)、l4.get(“parentguid”))
.leftOuterJoin(seq5,(l4,l5)->Objects.equals(l4.v4.get(“aoguid”)、l5.get(“parentguid”))
.leftOuterJoin(seq6,(l5,l6)->Objects.equals(l5.v5.get(“aoguid”)、l6.get(“parentguid”))
.leftOuterJoin(seq7,(l6,l7)->Objects.equals(l6.v6.get(“aoguid”)、l7.get(“parentguid”))
.parallel()
.forEach(it->{
System.out.println(“某些操作…”);
});
但这段代码并不编译。我如何修复它以使一切正常工作?

找到了一个解决方案:

public void saveES(List<Document> listDocs) {
    Seq<Document> l1 = seq(listDocs).filter(
            it -> ((Integer) it.get("currstatus") == 0)
    );

    l1
            .flatMap(level_1 -> seq(listDocs)
                    .filter(level_2 -> isNull(level_2.get("currstatus")) || ((Integer) level_2.get("currstatus") == 0))
                    .filter(level_2 -> Objects.equals(level_1.get("aoguid"), level_2.get("parentguid")))
                    .onEmpty(null)
                    .map(level_2 -> tuple(level_1, level_2))
            )
            .flatMap(level_1_2 -> //                            return tuple(level_1_2.v1, level_1_2.v2, level_3);
                    seq(listDocs)
                    .filter(level_3 -> isNull(level_3.get("currstatus")) || ((Integer) level_3.get("currstatus") == 0))
                    .filter(level_3 -> Objects.equals(level_1_2.v2.get("aoguid"), level_3.get("parentguid")))
                    .onEmpty(null)
                    .map(level_1_2::concat)
            )
            .flatMap(level_1_2_3 -> seq(listDocs)
                    .filter(level_4 -> isNull(level_4.get("currstatus")) || ((Integer) level_4.get("currstatus") == 0))
                    .filter(level_4 -> Objects.equals(level_1_2_3.v2.get("aoguid"), level_4.get("parentguid")))
                    .onEmpty(null)
                    .map(level_1_2_3::concat)
            )
            .flatMap(level_1_2_3_4 -> seq(listDocs)
                    .filter(level_5 -> isNull(level_5.get("currstatus")) || ((Integer) level_5.get("currstatus") == 0))
                    .filter(level_5 -> Objects.equals(level_1_2_3_4.v2.get("aoguid"), level_5.get("parentguid")))
                    .onEmpty(null)
                    .map(level_1_2_3_4::concat)
            )
            .flatMap(level_1_2_3_4_5 -> seq(listDocs)
                    .filter(level_6 -> isNull(level_6.get("currstatus")) || ((Integer) level_6.get("currstatus") == 0))
                    .filter(level_6 -> Objects.equals(level_1_2_3_4_5.v2.get("aoguid"), level_6.get("parentguid")))
                    .onEmpty(null)
                    .map(level_1_2_3_4_5::concat)
            )
            .flatMap(level_1_2_3_4_5_6 -> seq(listDocs)
                    .filter(level_7 -> isNull(level_7.get("currstatus")) || ((Integer) level_7.get("currstatus") == 0))
                    .filter(level_7 -> Objects.equals(level_1_2_3_4_5_6.v2.get("aoguid"), level_7.get("parentguid")))
                    .onEmpty(null)
                    .map(level_1_2_3_4_5_6::concat)
            )
            .parallel()
            .distinct()
            .forEach(it -> {
                log.info(
                        it.v1.get("formalname")
                                + " -> " + it.v2.get("formalname")
                                + " -> " + it.v3.get("formalname")
                                + " -> " + it.v4.get("formalname")
                                + " -> " + it.v5.get("formalname")
                                + " -> " + it.v6.get("formalname")
                                + " -> " + it.v7.get("formalname")
                );
            });
}
公共作废保存(列表文档){
Seq l1=Seq(listDocs).过滤器(
it->((整数)it.get(“currstatus”)==0)
);
l1
.flatMap(级别1->seq(列表文档)
.filter(level_2->isNull(level_2.get(“currstatus”))|(Integer)level_2.get(“currstatus”)==0)
.filter(level_2->Objects.equals(level_1.get(“aoguid”)、level_2.get(“parentguid”))
.onEmpty(空)
.map(level_2->tuple(level_1,level_2))
)
.flatMap(level_1_2->//返回元组(level_1_2.v1、level_1_2.v2、level_3);
序号(列表文档)
.filter(level_3->isNull(level_3.get(“currstatus”))|(Integer)level_3.get(“currstatus”)==0)
.filter(level_3->Objects.equals(level_1_2.v2.get(“aoguid”)、level_3.get(“parentguid”))
.onEmpty(空)
.map(1级2级::concat)
)
.flatMap(级别1\u 2\u 3->seq(列表文档)
.filter(level_4->isNull(level_4.get(“currstatus”))|(Integer)level_4.get(“currstatus”)==0)
.filter(level_4->Objects.equals(level_1_2_3.v2.get(“aoguid”)、level_4.get(“parentguid”))
.onEmpty(空)
.map(级别1\u 2\u 3::concat)
)
.flatMap(级别1\u 2\u 3\u 4->seq(列表文档)
.filter(level_5->isNull(level_5.get(“currstatus”))|(Integer)level_5.get(“currstatus”)==0)
.filter(level_5->Objects.equals(level_1_2_3_4.v2.get(“aoguid”)、level_5.get(“parentguid”))
.onEmpty(空)
.map(级别1\u 2\u 3\u 4::concat)
)
.flatMap(级别1\u 2\u 3\u 4\u 5->seq(列表文档)
.filter(level_6->isNull(level_6.get(“currstatus”))|(Integer)level_6.get(“currstatus”)==0)
.filter(level_6->Objects.equals(level_1_2_3_4_5.v2.get(“aoguid”)、level_6.get(“parentguid”))
.onEmpty(空)
.map(级别1\u 2\u 3\u 4\u 5::concat)
)
.flatMap(级别1\u 2\u 3\u 4\u 5\u 6->seq(列表文档)
.filter(level_7->isNull(level_7.get(“currstatus”))|(Integer)level_7.get(“currstatus”)==0)
.filter(level_7->Objects.equals(level_1_2_3_4_5_6.v2.get(“aoguid”)、level_7.get(“parentguid”))
.onEmpty(空)
.map(级别1\u 2\u 3\u 4\u 5\u 6::concat)
)
.parallel()
.distinct()
.forEach(it->{
log.info(
it.v1.get(“正式名称”)
+“->”+it.v2.get(“正式名称”)
+“->”+it.v3.get(“正式名称”)
+“->”+it.v4.get(“正式名称”)
+“->”+it.v5.get(“正式名称”)
+“->”+it.v6.get(“正式名称”)
+“->”+it.v7.get(“正式名称”)
);
});
}

前面的解决方案也是正确的,可能对某些人有用,但我将列出我最终寻求的解决方案。这是最终版本

@Override
public void saveES(List<Document> listDocs) {
    Seq<Document> root = seq(listDocs).filter(
            it -> ((Integer) it.get("currstatus") == 0) && ((Integer) it.get("aolevel") == 1)
    );

    root
            .leftOuterJoin(
                    seq(listDocs).filter(level_2 -> isNull(level_2.get("currstatus")) || ((Integer) level_2.get("currstatus") == 0)),
                    (a, b) -> checkObjects(a, b)
            )
            .leftOuterJoin(
                    seq(listDocs).filter(level_3 -> isNull(level_3.get("currstatus")) || ((Integer) level_3.get("currstatus") == 0)),
                    (a, b) -> checkObjects(a.v2, b)
            )
            .map(a -> a.v1.concat(a.v2))
            .leftOuterJoin(
                    seq(listDocs).filter(level_4 -> isNull(level_4.get("currstatus")) || ((Integer) level_4.get("currstatus") == 0)),
                    (a, b) -> checkObjects(a.v3, b)
            )
            .map(a -> a.v1.concat(a.v2))
            .leftOuterJoin(
                    seq(listDocs)
                            .filter(level_5 -> isNull(level_5.get("currstatus")) || (nonNull(level_5.get("currstatus")) && (Integer) level_5.get("currstatus") == 0)),
                    (a, b) -> checkObjects(a.v4, b)
            )
            .map(a -> a.v1.concat(a.v2))
            .leftOuterJoin(
                    seq(listDocs).filter(level_6 -> isNull(level_6.get("currstatus")) || ((Integer) level_6.get("currstatus") == 0)),
                    (a, b) -> checkObjects(a.v5, b)
            )
            .map(a -> a.v1.concat(a.v2))
            .leftOuterJoin(
                    seq(listDocs).filter(level_7 -> isNull(level_7.get("currstatus")) || ((Integer) level_7.get("currstatus") == 0)),
                    (a, b) -> checkObjects(a.v6, b)
            )
            .map(a -> a.v1.concat(a.v2))
            .parallel()
            .distinct()
            .forEach(it -> {
                List<Document> objects1 = (List<Document>) it.toList();
                String full = objects1.stream()
                        .filter(Objects::nonNull)
                        .map(doc -> String.join(" ", doc.getOrDefault("shortname", "") + ".", (String) doc.get("formalname")))
                        .collect(Collectors.joining(" "));

                List<Document> objects2 = (List<Document>) it.toList();
                List<Entry> entryList = objects2.stream()
                        .filter(Objects::nonNull)
                        .map(doc -> Entry.builder()
                                .aoid((String) doc.getOrDefault("aoid", ""))
                                .aoGuid((String) doc.getOrDefault("aoguid", ""))
                                .code((String) doc.getOrDefault("code", ""))
                                .offName((String) doc.getOrDefault("offname", ""))
                                .parentGuid((String) doc.getOrDefault("parentguid", ""))
                                .shortName((String) doc.getOrDefault("shortname", ""))
                                .aoLevel((Integer) doc.getOrDefault("aolevel", ""))
                                .postalCode((String) doc.getOrDefault("postalcode", ""))
                                .build())
                        .collect(Collectors.toList());
                log.info(full);
                Address address = new Address(full, entryList);
                searchService.save(address);
            });
}
@覆盖
公共作废保存(列表文档){
Seq root=Seq(listDocs).filter(
it->((整数)it.get(“currstatus”)==0&((整数)it.get(“aolevel”)==1)
);
根
.leftOuterJoin(
seq(listDocs).filter(level_2->isNull(level_2.get(“currstatus”))|(Integer)level_2.get(“currstatus”)==0),
(a,b)->检查对象(a,b)
)
.leftOuterJoin(
seq(listDocs).filter(level_3->isNull(level_3.get(“currstatus”))|(Integer)level_3.get(“currstatus”)==0),
(a,b)->检查对象(a.v2,b)
)
.map(a->a.v1.concat(a.v2))
.leftOuterJoin(
seq(listDocs).filter(level_4->isNull(level_4.get(“currstatus”))|(Integer)level_4.get(“currstatus”)==0),
(a,b)->checkObjects(a.v3,b)
)
.地图(a->a.v