Добавление нескольких отношений с помощью WITH, WHERE и UNWIND - PullRequest
0 голосов
/ 21 февраля 2019

У меня есть данные в следующей структуре:

{"id": "1", "name": "A. I. Lazarev", "org": "United States Department of State", "tags": [{"t": "Infrared"}, {"t": "Near-infrared spectroscopy"}, {"t": "Infrared astronomy"}, {"t": "Data collection"}], "pubs": [{"i": "1542417502", "r": 6}], }
{"id": "2", "name": "Stevan Spremo", "tags": [{"t": "Micro-g environment"}, {"t": "Antibiotics"}, {"t": "Bacteriology"}], "pubs": [{"i": "222163962", "r": 0}], }
{"id": "3", "name": "Bricchi G", "pubs": [{"i": "2417067698", "r": 1}, {"i": "2406980973", "r": 1}]}

Некоторые строки имеют теги, некоторые имеют организации, некоторые имеют оба, а некоторые нет.

Я хотел бы добавить отношения между (1) авторами и тегами, (2) авторами и организациями и (3) авторами и публикациями.У меня уже есть публикации в виде узлов, поэтому получить (3) довольно просто, как только я получу (1) и (2).

Я пытался использовать следующий код:

CALL apoc.periodic.iterate(
"CALL apoc.load.json('file:/test.txt') YIELD value AS q RETURN q",
"UNWIND q.id as id
CREATE (a:Author {id:id, name:q.name, citations:q.n_citation, publications:q.n_pubs})
WITH q, a
UNWIND q.tags as tags
MERGE (t:Tag {{name: tags.t}})
CREATE (a)-[:HAS_TAGS]->(t)
WITH q, a
WHERE q.org is not null
MERGE (o:Organization {name: q.org})
CREATE (a)-[:AFFILIATED_WITH]->(o)",
{batchSize:10000, iterateList:true, parallel:false})

Теги и организации отображаются в данных несколько раз, но в каждом из них должен быть только один узел, поэтому я использовалMERGE для создания уникальных узлов для них.

Проблема со следующим кодом заключается в том, что он создает повторяющиеся отношения AFFILIATED_WITH - фактически он создает такое же количество AFFILIATED_WITH отношений, что и теги.

Как я могу изменить запрос на шифрование, чтобы он не создавал дублирующиеся отношения?

1 Ответ

0 голосов
/ 22 февраля 2019

После этого предложения:

UNWIND q.tags as tags

в вашем запросе будет столько строк данных, сколько тегов для текущего q (в каждой строке будет q, a, id, tags значений).Последующие операции будут выполняться один раз для каждой строки данных.Вот почему вы создаете слишком много AFFILIATED_WITH отношений.

Чтобы решить вашу проблему, вы должны соответствующим образом сократить количество строк данных в соответствующее время (и это также ускорит вашу обработку, так какненужные повторные операции будут исключены).В вашем случае вы можете просто изменить второе предложение WITH q, a на WITH DISTINCT q, a:

CALL apoc.periodic.iterate(
  "CALL apoc.load.json('file:///test.txt') YIELD value AS q RETURN q",
  "CREATE (a:Author {id:q.id, name:q.name, citations:q.n_citation, publications:q.n_pubs})
   WITH q, a
   UNWIND q.tags as tags
   MERGE (t:Tag {name: tags.t})
   CREATE (a)-[:HAS_TAGS]->(t)
   WITH DISTINCT q, a
   WHERE q.org is not null
   MERGE (o:Organization {name: q.org})
   CREATE (a)-[:AFFILIATED_WITH]->(o)",
  {batchSize:10000, iterateList:true, parallel:false}
)

Я также упростил запрос, удалив ненужное предложение UNWIND q.id as id и исправив некоторые синтаксические проблемы.

[ОБНОВЛЕНО]

Если вы хотите добавить отношения AUTHORED (как требуется в комментариях к этому ответу), вы должны сделать это до , когда вы создадите AFFILIATED_WITH отношений - поскольку предложение WHERE q.org is not null отфильтровывает некоторые q узлы.Кроме того, всякий раз, когда вы используете CREATE для создания отношения, Cypher требует, чтобы вы указали направление для отношения.

CALL apoc.periodic.iterate(
  "CALL apoc.load.json('file:///test.txt') YIELD value AS q RETURN q",
  "CREATE (a:Author {id:q.id, name:q.name, citations:q.n_citation, publications:q.n_pubs})
   WITH q, a
   UNWIND q.tags as tags
   MERGE (t:Tag {name: tags.t})
   CREATE (a)-[:HAS_TAGS]->(t)
   WITH DISTINCT q, a
   UNWIND q.pubs as pubs
   MERGE (p:Quanta {id: pubs.i})
   CREATE (a)-[r:AUTHORED {rank: pubs.r}]->(p)
   WITH q, a
   WHERE q.org is not null
   MERGE (o:Organization {name: q.org})
   CREATE (a)-[:AFFILIATED_WITH]->(o)",
  {batchSize:10000, iterateList:true, parallel:false}
)
Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...