Head's Up! These forums are read-only. All users and content have migrated. Please join us at community.neo4j.com.
10-23-2020 06:02 AM
I have to create many to many relationship. here are my csv dataset screenshot.
There are 12 different dishes type nodes.
and 14 different person type nodes.
1 Person can cook upto 5 dishes and multiple person can cook multiple dishes. The dishes IDs are mentioned in columns. I have to save CookingStartTime value in Edge.
Here is my query.
LOAD CSV WITH HEADERS FROM 'file:///Food.csv' AS TweettoHashtag
MATCH (m:Persons),(n:Dishes) WHERE m.Dish1 = n.iD Merge (m)-[:canCook {StartTime: datetime(CookingStartTime.Time)} ]->(n)
It should create 13 links. but it create 13x14= 182 links. (Because there are 14 total rows in table 2)
So it iterates 14 times and create 13 edges. I know my query have problem. buy how to fix it. I am not able to sort out. if there is anyone who can mention if my query have problem or my input data should be saved in different way?
I must have to do this by reading csv file. this is subset of dataset. real dataset would be large and more complicated.
10-23-2020 10:37 AM
Welcome Alfa!
I believe you are getting 13x14 because
MATCH (m:Persons),(n:Dishes)
is a cartesian product
have you tried dropping the (n:Dishes) and then change the WHERE clause skip null dish values?
something like this,
LOAD CSV WITH HEADERS FROM 'file:///Food.csv' AS TweettoHashtag
MATCH (m:Persons)
WHERE m.Dish1 is not null
MERGE (m)-[:canCook {StartTime: datetime(CookingStartTime.Time)} ]->(:Dish {id:m.Dish1})
Think about the edges you want, which are I believe something like this...
personid dish
121 1
122 2
122 3
123 1
124 1
10-26-2020 04:37 AM
No. I think this query have problem. Result of query.
Added 182 labels, created 182 nodes, set 364 properties, created 182 relationships, completed after 238 ms.
10-27-2020 04:40 PM
Try this. I created dishes csv file and small version of your second table.
Here is my solution:
LOAD CSV WITH HEADERS FROM 'file:///person.csv' AS row
WITH [COALESCE(toInteger(row.Dish1), 0), COALESCE(toInteger(row.Dish2), 0), COALESCE(toInteger(row.Dish3), 0), COALESCE(toInteger(row.Dish4), 0), COALESCE(toInteger(row.Dish5), 0)] as ids, row
MERGE (m:Persons {id: toInteger(row.PersonID)})
WITH row, ids, m
MATCH (d:Dish) where d.id in ids
WITH row, ids, m, d, split(row.CookingStartTime, 'T') as dte
MERGE (m)-[:canCook {StartTime: time(dte[1])} ]->(d)
Result:
10-26-2020 03:22 PM
I think you need to rethink your CSV format for import. The first one for the dishes alone is fine.
A much simpler CSV for the other would be:
PersonID CookingStartTime DishID
A single person may have multiple entries, one per dish that they cooked.
An import query for this CSV would be much simpler. Let's assume both :Dish and :Person nodes were already created (probably best to stick with singular terms instead of plural for labels), and both of them are using ID
for their id properties.
LOAD CSV WITH HEADERS FROM 'file:///Food.csv' AS row
MATCH (p:Person)
WHERE p.ID = row.PersonID
MATCH (d:Dish)
WHERE d.ID = row.DishID
MERGE (p)-[:canCook {StartTime: datetime(row.CookingStartTime} ]->(d)
All the sessions of the conference are now available online