2016-12-06 2 views
0

Ich möchte mit neo4j die Benutzer auswählen, die Anzahl der Action-Filme, die sie angeschaut haben und wie viele dieser Action-Filme von jedem Benutzer von Roland Emmerich geleitet wurde.Neo4j unabhängige Auswahl über mehrere Match-Klauseln

habe ich versucht, in verschiedenen Formen, diese Abfrage:

match (u:User)-[:watched]->(m:Movie)-[belongs_to]->  
(Category{category_name:"Action"}) with count(m) as actionMovies, u 
match (m:Movie)<-[directed]-(Director{director_name:"Roland Emmerich"}) 
return u, count(m) as MoviesFromRE, actionMovies 

Aber die Ausführung der Abfrage nie beendet. Also nehme ich an, ich mache so etwas wie ein Cross Join.

Eigentlich erwarte ich, die erste Zählung unabhängig von der Sekunde zu haben, da sie bereits berechnet wird, wenn der Compiler zur zweiten Übereinstimmungsklausel kommt.

Hier ist der relevante db Ansicht

Overview of used database (Movies)

Vielen Dank für alle Anregungen und hilft

Ok nach Ziffer der Tippfehler und einschließlich Filme in loszuwerden:

match (u:User)-[:watched]->(m:Movie)-[:belongs_to]->  
(:Category{category_name:"Action"}) with count(m) as actionMovies, u, m 
match (m)<-[:directed]-(:Director{director_name:"Roland Emmerich"}) 
return u, count(m) as MoviesFromRE, actionMovies order by u.user_name 

Jetzt bekomme ich für ActionMovies immer 1. Ich denke es liegt daran, dass ich mich jetzt erstmal mit der Klausel von Movies zusammenfasse. Ich denke, ich brauche einen Weg, die Filme von der ersten Klausel zur zweiten zu bringen, aber nicht meine erste von ihnen zu gruppieren.

+0

Sie haben ein paar seltsamen Dinge in Ihrer Anfrage, nicht sicher, ob sie Fehler sind, wenn es hier einfügen, oder wenn sie existieren in der Abfragen, die Sie ausführen möchten. Denken Sie daran, dass den Beziehungstypen ein ':' vorangestellt wird, aber 'gehört' und' gerichtet' in Ihren Abfragen nicht, was bedeutet, dass es sich um Variablen handelt, die zu jeder Art von Beziehung passen. Ähnlich ist 'Director' in Ihrer Anfrage kein Label (nein': '), also ist es eine Variable, die zu jedem Knoten mit einer Eigenschaft' director_name' auf "Roland Emmerich" passt. Ähnlich wie bei 'Category'. – InverseFalcon

+0

Auch Ihr zweites Spiel ist vollständig von Ihrem ersten getrennt. Unter der Annahme, dass die Beziehung und der Director-Knoten behoben sind, so dass sie keine Variablen sind, Sie nach allen Filmen von Roland Emmerich fragen, und das hat nichts mit Filmen zu tun, die von einem Nutzer gesehen werden, wird die Anzahl der Filme konstant sein Roland Emmerich hat Regie geführt. Das liegt daran, dass die "m" -Variable, die an: Movies gebunden ist, nicht das gleiche "m" ist wie Ihre erste Übereinstimmung ( – InverseFalcon

+0

@InverseFalcon) Ich werde meine Tippfehler los und postete den neuen Code mit Ihrem Vorschlag der Klausel mit. Leider erhalte ich ein falsches Ergebnis, da Action Movies jetzt immer 1 – dbmongo

Antwort

2

Der Grund, warum Sie immer 1 für actionMovies immer in dieser Klausel ist:

WITH COUNT(m) AS actionMovies, u, m 

Diese Klausel (teilweise) sagt: „Die Zahl der m Knoten für jedes einzigartiges Paar u und m Knoten zählen ". Dieser Zählwert muss immer 1.

sein Diese Abfrage sollte besser funktionieren:

MATCH (u:User)-[:watched]->(am:Movie)-[:belongs_to]->(:Category{category_name:"Action"}) 
WITH u, COLLECT(am) AS ams 
UNWIND ams AS m 
OPTIONAL MATCH (m)<-[dir:directed]-(:Director{director_name:"Roland Emmerich"}) 
RETURN u, COUNT(dir) AS MoviesFromRE, SIZE(ams) AS actionMovies 
ORDER BY u.user_name; 
+1

sind. Ich denke, OPTIONAL MATCH könnte deinen COUNT (m) in der Rückkehr wegwerfen, da es die Anzahl der Zeilen nicht beeinflusst. Ich denke, du brauchst eine Feinabstimmung, um das zu funktionieren. – InverseFalcon

+0

@InverseFalcon Netter Fang. Ziemlich subtil. "OPTIONAL" vom zweiten "MATCH" entfernt. – cybersam

+1

Ich bin mir nicht sicher, ob das auch funktionieren wird. Da es jetzt ein MATCH ist, wird es Reihen mit Filmen, die nicht von Roland Emmerich geleitet werden, eliminieren, so dass jeder Benutzer, der keinen dieser Roland Emmerich gerichteten Filme gesehen hat, nicht in der Ergebnismenge erscheint.Vielleicht eliminiere das MATCH und verwende 'SIZE ((m) <- [: directed] - (: Director {director_name:" Roland Emmerich "}))'. Alternativ kann ein FILTER mit einigen Änderungen an der Abfrage gut funktionieren. – InverseFalcon

Verwandte Themen