У меня есть два документа в эластичном поиске со следующими значениями
uid preferences
1 [10,20,30,40,50,60,70,80,100]
2 [20,70,30,100,1000,77,45]
Можем ли мы каким-либо образом пересечь массив настроек для этих двух записей и получить результат [20,70,30,100]
? В настоящее время мы получаем эти две записи на сервер приложений и выполняем пересечение, но хотели проверить, есть ли какой-либо прямой способ получить значения пересечения напрямую из Elasticsearch. Спасибо.
Спасибо @JoeSorocin за ваш комментарий. Пара из 2, как указано в примере, в порядке.
Я бы решил эту проблему, используя параметризованную агрегацию метрик по сценарию. Вот более читаемая версия:
{
"size": 0,
"query": {
"terms": {
"id": [
1,
2
]
}
},
"aggs": {
"preferences_intersection": {
"scripted_metric": {
"init_script": "state.shared_vals = [];",
"map_script": "state.shared_vals.addAll(new ArrayList(doc['preferences']));",
"combine_script": """
return state.shared_vals.stream()
.filter(i -> Collections.frequency(state.shared_vals, i) >= params.compared_docs_count)
.sorted((o1, o2) -> o1.compareTo(o2))
.collect(Collectors.toCollection(TreeSet::new))
""",
"reduce_script": "return states[0]",
"params": {
"compared_docs_count": 2
}
}
}
}
}
Обратите внимание, как запрос terms
был применен вместе с params.compared_docs_count
, чтобы мы могли проверить количество вхождений общих значений.
Вот компактная версия запроса без тройных кавычек:
{"size":0,"query":{"terms":{"id":[1,2]}},"aggs":{"preferences_intersection":{"scripted_metric":{"init_script":"state.shared_vals = [];","map_script":"state.shared_vals.addAll(new ArrayList(doc['preferences']));","combine_script":" return state.shared_vals.stream()\n .filter(i -> Collections.frequency(state.shared_vals, i) >= params.compared_docs_count)\n .sorted((o1, o2) -> o1.compareTo(o2))\n .collect(Collectors.toCollection(TreeSet::new))","reduce_script":"return states[0]","params":{"compared_docs_count":2}}}}}
Спасибо @JoeSorocin за ваш ответ. Поскольку это сценарий, основанный на размышлениях о проблемах с производительностью. Удачи вашему «Руководству по Elasticsearch»
Спасибо! Да, скрипты, как правило, медленные, но в этом мы просматриваем только 2 документа благодаря запросу terms
, поэтому я бы не стал об этом беспокоиться.
Пересекаются значения для чего? На группу идентификаторов документов? Или просто пара 2, как в вашем примере?