缩短可选匹配查询

时间:2015-08-10 16:55:38

标签: neo4j neo4jclient

我在这里有一个查询,如果可能的话我想缩短。 查询说如果我发布文档,或者我的部门中的某个人发布了我希望返回的文档,如果不符合这两个标准中的任何一个,则不返回任何内容,一切都很好。 但是我不喜欢我必须这样做的方式,所以有人可以快速查看并告诉我是否有更好的方法

optional match(document:Document{id:6})-[:SHARED]-()-[:IN_DEPARTMENT_WITH]-(me:Person{Email:'user@outlook.com'})
optional match(document2:Document{id:6})-[:SHARED]-(me2:Person{Email:'user@outlook.com'})
return document,me,document2,me2

因为我必须返回文件,或者文件2,以及我或者me2,这取决于哪个匹配得到了打击它会让事情变得有点混乱,有没有办法让它更清洁,所以哪个匹配得到一个命中我返回文件和我?

由于

2 个答案:

答案 0 :(得分:1)

在这种情况下,我会使用零长度路径作为可选匹配的一种代理。考虑这个示例数据集:

CREATE (doc1:Document {id:1}),
       (doc2:Document {id:2}),
       (doc3:Document {id:3}),

       (you:Person {Email:"shaine@outlook.com"}),
       (colleague:Person {Email:"nicole@outlook.com"}),
       (nonColleague:Person {Email:"julian@outlook.com"}),

       (you)-[:IN_DEPARTMENT_WITH]->(colleague),
       (you)-[:SHARED]->(doc1),
       (colleague)-[:SHARED]->(doc2),
       (nonColleague)-[:SHARED]->(doc3);

对于文档1,您共享了它,因此我们希望将它作为共享者返回。在文档2的情况下,您的同事分享了它,因此我们希望将您的同事作为共享者返回。就文件3而言,由于您和您的同事都没有共享该文件,我们不希望得到任何结果。

我们可以在匹配[:IN_DEPARTMENT_WITH]关系时使用零长度路径编写涵盖所有三种方案的单个查询。

文件1:

MATCH (colleague:Person)-[:SHARED]->(doc:Document { id:1 }),
      (:Person { Email:"shaine@outlook.com" })-[:IN_DEPARTMENT_WITH*0..1]-(colleague)
RETURN colleague.Email, doc.id;

colleague.Email     doc.id
shaine@outlook.com  1

文件2:

MATCH (colleague:Person)-[:SHARED]->(doc:Document { id:2 }),
      (:Person { Email:"shaine@outlook.com" })-[:IN_DEPARTMENT_WITH*0..1]-(colleague)
RETURN colleague.Email, doc.id;

colleague.Email     doc.id
nicole@outlook.com  2

文件3:

MATCH (colleague:Person)-[:SHARED]->(doc:Document { id:3 }),
      (:Person { Email:"shaine@outlook.com" })-[:IN_DEPARTMENT_WITH*0..1]-(colleague)
RETURN colleague.Email, doc.id;

No rows.

请注意,您有时是"同事&#34 ;;在您共享文档的情况下,您将colleague与长度为零的路径匹配。你可以在这里玩它:http://console.neo4j.org/r/yhyrqu

答案 1 :(得分:0)

这对你有用吗?

MATCH (me:Person{Email:'user@outlook.com'}), (doc:Document{id:6})
OPTIONAL MATCH (doc)-[r:SHARED]-(me)
WITH me, doc, (CASE WHEN r IS NULL THEN [] ELSE [me] END) AS myself
OPTIONAL MATCH (doc)-[:SHARED]-(p)-[:IN_DEPARTMENT_WITH]-(me)
RETURN doc, COLLECT(p) + myself AS result;

此查询仅匹配medoc一次,并合并两个(可能为空)集合以到达生成的人员集合。如果MATCH(在第一行)找不到匹配项,则结果将不包含任何行。