Complex query with agregation in where clause

感情迁移 提交于 2019-12-24 17:00:03

问题


Suppose that i have a graph in which for each pair of nodes m,n of type BallT there can be a node k of type BallD that connects them through relationships of type Rel, that is, there can be multiple patterns of the kind p=(m:BallT)-[r:Rel]-(k:BallD)-[s:Rel]-(n:BallT). For a given node m (satisfying for example m.key="whatever") let's call Nmn the number of BallD connecting m and some node n and N the total number of BallD nodes. For this given node m how can i found all nodes n such that Nmn > N/2 and order the results by Nnm? I'm trying the query:

match (D:BallD)
with count(D) as N
match (m:BallT {key:"whatever"})-[r]-(d:BallD)-[s]-(n:BallT)
with N, distinct n as n_dist, count(d) as Nmn
where Nmn >= N
return n_dist
order by Nmn

but i'm getting

Invalid input 't': expected whitespace, comment, node labels, MapLiteral, a parameter, a relationship pattern

回答1:


Does this query do what you want?

MATCH (D:BallD)
WITH count(D) as N
MATCH (m:BallT {key:"whatever"})--(d:BallD)--(n:BallT)
WITH N, n, count(d) as Nmn
WHERE Nmn >= N/2
RETURN n, Nmn
ORDER BY Nmn
  • When using an aggregation function (like count) over a value (like n), you do not need to use DISTINCT to qualify the value that you are aggregating over -- that is done automatically for you.

  • The ORDER BY argument must refer to a part of the returned values.

  • Also, I corrected the WHERE clause to use N/2.




回答2:


Just for future reference!! What i was trying to do: I have an array of keys ["k1",..,"kn"] that occur in a map d. For each key ki (i=1,..,n) i want to create nodes for it (if not already created), count the number of occurrences of ki in that map as well as to increment the total number of occurrences of ki in all maps that i eventually going to insert in database. To perform this bunch of create i perform this query:

create (d:Map)
with d
unwind [k1,...,kn] as k0
with distinct k0 as kd0, count(k0) as c, d
merge (k:Key {key: kd0})
on create set t.count = c, t.mapCount = 1
on match set t.count = t.count + c, t.mapCount = t.mapCount + 1
create (d)-[r:Contains {count: c}]->(t)
return t

Note that in this query i register the total number of occurrences of ki in the node that represents it and the number of occurrences of it in some map d in the relationship (of type Contains) that relates both (sorry my bad english! hehe)

Afterwards, lets say i want to find all keys k that co-occur with keys [k1,...,kn] (i.e., through some map d) but restricted to those keys k that co-occur "a lot" with ki (i.e., the number of maps that relates k and ki with i=1,..,n is bigger than M), but do not occur "a lot" in general (i.e., the number of maps that k occur in general is less than N). In this case i perform the following query:

unwind [k1,...,kn] as ki
match (:Key {key: ki})<-[r:Contains]-(d:Map)-[s:Contains]->(k:Key)
where k.mapCount < N
with distinct(k) as kd, count(d) as x
where x > M
return kd
order by x desc, kd.count desc
limit 5

Note that in this query i order the results first by x (the number of maps that contains both ki and k) and second by the number of occurrences of k, i.e., if two k's has the same x, then put first the k's with higher count.

Thanks a lot for the replies guys.... i have never been a frequent user of StackOverflow, but now i think i gonna use it a lot!! :)



来源:https://stackoverflow.com/questions/29100010/complex-query-with-agregation-in-where-clause

标签
易学教程内所有资源均来自网络或用户发布的内容,如有违反法律规定的内容欢迎反馈
该文章没有解决你所遇到的问题?点击提问,说说你的问题,让更多的人一起探讨吧!