2016-01-09 4 views
0

Я обнаруживаю, что база данных графиков логична, читает Руководство по базе данных диаграмм O'Reilly. Я в восторге, но все еще есть вопрос.Заказ отношения внутри базы данных графа (neo4j)

Мои первые вопросы касаются отношений. Предположим, я хочу смоделировать связь между текстами и рукописями, которые их обрабатывают.

Так что я буду иметь два типа узла (две метки):

  • Рукописи
  • Тексты

Одна рукопись может содержать несколько текстов и один текст может содержаться в нескольких рукописях , Поэтому у меня будет что-то вроде (ms:MS {identification}) -[:CONTAINS]->(txt:TXT {identification}).

Но вопрос в том, как я могу хранить и запрашивать порядок текстов в манускрипте. Должен ли я добавить «порядок» в отношение CONTAINS? Как насчет производительности в запрашивая:

  • получить список заказа текстов contening в конкретной рукописи
  • знать, в котором рукописях текста есть до и других текстов, и в котором он после того же другого текста. Это, например, я хочу знать все рукописи, где текст «А» находится перед «В», и все рукописи, где текст «В» находится перед текстом «А».
+0

перед обновлением моего ответа с последним уточнением, вы хотите, чтобы получить как списки рукописей (A до B, и B, прежде A) в том же запросе? или вы планируете иметь один запрос и использовать его дважды с обратным порядком текста? – saljuama

+0

о, это может быть в двух запросах, или в одном, не имеет значения. –

ответ

1

Быстрый ответ, да, атрибут заказа на краю CONTAINS, и что касается производительности, очень быстро.

Следует ли добавить «порядок» в отношения СОДЕРЖИТ?

Да, имеет смысл добавить свойство заказа в CONTAINS кромки.

Почему это имеет смысл? Представим себе другие места для хранения упорядочения текстов в рукописи:

a) Сохранение порядка текстов в рукописи: для этого вам нужно будет сохранить список [ текст, порядок], чтобы узнать, какой текст находится в каком положении.

b) Сохранение порядка текстов в самом тексте: в этом случае в текстовом узле вам необходимо сохранить список [рукопись, заказ], чтобы узнать, в каком положении рукописи текст присутствует, для каждой из разных рукописей текст появляется.

Хотя эти 2 являются допустимыми параметрами для моделирования, когда вы пытаетесь выполнить запросы с этими двумя различными вариантами, вы сделали это сложнее для себя, когда дело доходит до вставлять, редактировать, удалять или запрашивать узлы.

насчет производительности в запрашивая:

Прежде чем ответить на конкретные сценарии, просто напоминание, чтобы иметь в виду: доступ к узлу и пересекающих отношения в Neo4j, оба имеют стоимость O(1) ,

Редактировать: дополнительная информация о производительности в этом другом question from SO

получить список заказа текстов contening в конкретной рукописи

Так рукопись с n текстов, общее стоимость операции по извлечению всех текстов будет примерно O(n), и все они будут отсортированы, можно взять стоимость O(n*log n), так что это будет зависеть от количества тексты на одну рукопись.

Update: Если вы хотите, чтобы сравнить стоимость с реляционными базами данных, в соответствии с просьбой в комментарии, ну, asuming подобную модель, с 3-мя столами, один для рукописей, один для текста, и один для отношений с порядок, следуя принципу «многие ко многим со свойствами». Вы закончите сканирование всей таблицы отношений, что будет означать, что стоимость будет выше, поскольку она будет зависеть от всех существующих отношений между всеми манускриптами и текстом, а не только подмножеством.

известно, в каких рукописях текст предшествует и другие тексты и в котором он находится после того же текста. Это, например, я хочу знать все рукописи, где текст «А» находится перед «В», и все рукописи, где текст «В» находится перед текстом «А».

Зная, в котором рукописи текст находится, так же легко, как пересекающая все входящие CONTAINS отношений, то есть эта операция O(n), будучи n количеством рукописей появляется текст.

Но для рукописи, где текст A появляется перед текстом B, это немного сложнее и дороже, я попытаюсь сломать его:

Учитывая, что n - это количество рукописей, в которых появляется текст A, и m - количество рукописей текста B появляется.

  1. Сначала необходимо будет найти все рукописи текст А находится в, а также все рукописи текст B находится в. Стоимость этой операции O(n+m), которая до сих пор линейная

  2. Затем необходимо отфильтровать эти списки, чтобы найти рукописи, которые появляются в обоих списках. Это снова стоит O(n+m).

  3. И, наконец, фильтровать снова манифестах, где исходящие CONTAINS края, имеют свойство порядка, где порядок CONTAINS в текст А меньше, чем свойство порядка CONTAINS к тексту B. Стоимость этого будет примерно O(k) где k является размером списка рукописей, результат шага 2.

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

+0

Что значит «манифест»? Я уточню свой вопрос. –

+0

oh snap, я имел в виду манускрипты, не знаю почему я изменил это в своем уме. я обновлю и изменю эти – saljuama

+0

Хорошо, но я до сих пор не понимаю: «Если вы попытаетесь сохранить его в рукописи, вы в конце концов вложите все тексты в рукопись, и если вы намереваетесь это сделать, лучше используйте хранилище документов ". В любом случае, мой вопрос: «Получить порядок текстов в manuscritpts, лучше использовать реляционную или графическую базу данных». В обоих случаях будет O (n * log n)? –

0

Оба являются разумными.

Проще поддерживать, если вы создаете: СЛЕДУЮЩИЕ отношения между вашими текстами.

Для оформления заказа вы должны обновить их все, если вы удалите или вставьте один текст.

При добавлении новых текстов вы просто добавляете их в последний текст с соотношением: NEXT.

Тогда вы можете получить все тексты рукописи в порядке с:

MATCH (m:MS {id:"..."})-[:CONTAINS]->()-[:NEXT*0..]->(text:TXT) 
RETURN m, collect(distinct text); 
+0

ok, но в этом случае я должен отметить связь [: NEXT * 0 ..] с идентификатором manuscript, так как тот же текст может быть в нескольких рукописях. –

+0

обычно не следует добавлять тексты между текстами. Рукописи были написаны один и не были изменены после него ;-) –

+0

ну, с таким подходом вы получите их уже отсортированные, и первый результат выполнения запроса будет лучше, вплоть до 'O (n)', но нужно быть осторожным , потому что текст может появляться в нескольких рукописях, поэтому, возможно, для краев 'NEXT' потребуется свойство с идентификатором manuscript. – saljuama

Смежные вопросы