ES filter和post_filter的区别
在Elasticsearch中,过滤搜索的结果是我们经常要做的事。在我刚开始接触 Elasticsearch,我就了解到有两种可以过滤搜索结果的方法。当时还不是很明白,为什么有的地方用 filter,而有的地方需要使用到 post_filter。在今天的文章中,我来用一个鲜活的例子来进行展示。
总体说来,我们可以使用如下的两个方法来过滤搜索的结果:
使用带有 filter 子句的布尔查询。搜索请求将布尔过滤器应用于搜索命中和聚合。
使用搜索 API 的 post_filter参数。搜索请求仅将 post_filter应用于搜索命中,而不是聚合。你可以使用 post_filter根据更广泛的结果集计算聚合,然后进一步缩小结果。讲得通俗一点:在已经计算聚合之后,post_filter 将应用于搜索请求最后的搜索命中。从这里的描述中,我们可以看出来,post_filter的使用和 aggregation 相关。
你还可以在 post_filter之后重新对命中进行评分,以提高相关性并重新排序结果
Post filter
当你使用 post_filter 参数过滤搜索结果时,会在计算聚合后过滤搜索命中。 Post filter 对聚合结果没有影响。
例如,你销售的衬衫具有以下属性:
PUT shirts
{
"mappings": {
"properties": {
"brand": { "type": "keyword"},
"color": { "type": "keyword"},
"model": { "type": "keyword"}
}
}
}
我们使用如下的命令来摄入 3 个文档:
PUT shirts/_doc/1?refresh
{
"brand": "gucci",
"color": "red",
"model": "slim"
}
PUT shirts/_doc/2?refresh
{
"brand": "polo",
"color": "red",
"model": "large"
}
PUT shirts/_doc/3?refresh
{
"brand": "polo",
"color": "blue",
"model": "medium"
}
假想你有一个用户,他想买一个 red 的衣服。通常你会使用如下的 bool query:
GET shirts/_search?filter_path=**.hits
{
"query": {
"bool": {
"filter": [
{
"term": {
"color": "red"
}