Гремлин нашел самое высокое соответствие - PullRequest
3 голосов
/ 07 июля 2019

Я планирую использовать базу данных графиков (AWS Neptune), к которой можно обращаться с Gremlin, в качестве базы знаний. КБ будет использоваться в качестве инструмента классификации для объектов с несколькими функциями. Для простоты в этом примере я использую геометрические фигуры для кодирования свойств моих объектов. Предположим, я хочу классифицировать точки, которые могут быть связаны с квадратами, треугольниками и кругами. У меня есть план возможных отношений Точек с возможными Квадратами, Треугольниками и Кругами на графике, как показано на рисунке ниже.

enter image description here

Создано с:


g.addV('Square').property(id, 'S_A')
 .addV('Square').property(id, 'S_B')
 .addV('Circle').property(id, 'C_A')
 .addV('Triangle').property(id, 'T_A')
 .addV('Triangle').property(id, 'T_B')
 .addV('Point').property(id, 'P1')
 .addV('Point').property(id, 'P2')
 .addV('Point').property(id, 'P3')

g.V('P1').addE('Has_Triangle').to(g.V('T_B'))
g.V('P2').addE('Has_Triangle').to(g.V('T_A'))
g.V('P1').addE('Has_Square').to(g.V('S_A'))
g.V('P2').addE('Has_Square').to(g.V('S_A'))
g.V('P2').addE('Has_Circle').to(g.V('C_A'))
g.V('P3').addE('Has_Circle').to(g.V('C_A'))
g.V('P3').addE('Has_Square').to(g.V('S_B'))


К различным объектам относятся, например, точки, квадраты, треугольники, круги.

Итак, моя конечная цель - найти Точку, которая удовлетворяет наибольшему числу условий. Э.Г.

g.V().hasLabel('Point').where(and(
    out('Has_Triangle').hasId('T_A'),
    out('Has_Circle').hasId('C_A'),
    out('Has_Square').hasId('S_A')
))

// ==>v[P2]

Приведенный выше запрос очень хорошо подходит для классификации точки (a) со свойствами (T_A,S_A,C_A) соответственно, например, как тип Point 2 (P2). Но если бы мне пришлось использовать тот же запрос для классификации точки со свойствами (C_A,S_B,T_X), например:

g.V().hasLabel('Point').where(and(
    out('Has_Triangle').hasId('T_X'),
    out('Has_Circle').hasId('C_A'),
    out('Has_Square').hasId('S_B')
))

Запрос не сможет классифицировать эту точку как точку 3 (P3), поскольку в КБ нет известного свойства Triangle для P3.

Есть ли способ, которым я могу выразить запрос, который возвращает вершину с наибольшим соответствием , которое в этом случае будет P3?

Заранее спасибо.

EDIT

Лучшая идея для решения этой проблемы - поместить значения часовых для свойств КБ, которые не существуют. Затем измените запрос, чтобы он соответствовал каждому точному свойству или значению часового. Но это означает, что если я добавлю новый «тип» свойства к точке в будущем, например, Точка Has_Hexagon, чем мне нужно, чтобы добавить часовой шестиугольник ко всем точкам моего графика.

РЕДАКТИРОВАТЬ 2

Добавлен скрипт Gremlin, который создает примеры данных

1 Ответ

3 голосов
/ 08 июля 2019

Вы можете использовать шаг choose(), чтобы увеличить счетчик (sack) для каждого совпадения, затем упорядочить по значениям счетчика (по убыванию) и выбрать первый (самое высокое совпадение).

gremlin> g.withSack(0).V().hasLabel('Point').
           choose(out('Has_Triangle').hasId('T_A'), sack(sum).by(constant(1))).
           choose(out('Has_Circle').hasId('T_A'),   sack(sum).by(constant(1))).
           choose(out('Has_Square').hasId('T_A'),   sack(sum).by(constant(1))).
           order().
             by(sack(), decr).
           limit(1)
==>v[P2]

gremlin> g.withSack(0).V().hasLabel('Point').
           choose(out('Has_Triangle').hasId('T_X'), sack(sum).by(constant(1))).
           choose(out('Has_Circle').hasId('T_A'),   sack(sum).by(constant(1))).
           choose(out('Has_Square').hasId('S_B'),   sack(sum).by(constant(1))).
           order().
             by(sack(), decr).
           limit(1)
==>v[P3]

Каждый choose() шаг в запросах выше может быть прочитан как if (condition) increment-counter.В любом случае, независимо от того, выполнено ли условие или нет, исходная вершина (Point) будет отправлена ​​с помощью шага choose.

...