Elasticsearch计算距离,根据距离排序,地理点和地理多边形范围查找

这篇具有很好参考价值的文章主要介绍了Elasticsearch计算距离,根据距离排序,地理点和地理多边形范围查找。希望对大家有所帮助。如果存在错误或未考虑完全的地方,请大家不吝赐教,您也可以点击"举报违法"按钮提交疑问。

Elasticsearch 计算距离,根据距离排序,地理点和地理多边形范围查找

总结

Elasticsearch 计算并返回距离一共有两种方法:sortscript_fields

环境概述

  • CentOS 7.6
  • Elasticsearch 7.10

创建索引

PUT /scenic_spot
{
  "mappings": {
    "properties": {
      "id": {
        "type": "keyword"
      },
      "name": {
        "type": "text"
      },
      "pin": {
        "properties": {
          "location": {
            "type": "geo_point"
          }
        }
      }
    }
  },
  "settings": {
    "number_of_replicas": 3,
    "number_of_shards": 3
  }
}

索引数据

PUT /scenic_spot/_doc/1
{
  "id": 1,
  "name": "恭王府景区",
  "pin": {
    "location": {
      "lat": 31.007925,
      "lon": 103.607572
    }
  }
}

PUT /scenic_spot/_doc/2
{
  "id": 2,
  "name": "故宫博物院",
  "pin": {
    "location": {
      "lat": 39.917248,
      "lon": 116.397176
    }
  }
}

PUT /scenic_spot/_doc/3
{
  "id": 3,
  "name": "天坛公园",
  "pin": {
    "location": {
      "lat": 39.881265,
      "lon": 116.410638
    }
  }
}

PUT /scenic_spot/_doc/4
{
  "id": 4,
  "name": "颐和园",
  "pin": {
    "location": {
      "lat": 39.991664,
      "lon": 116.271966
    }
  }
}

PUT /scenic_spot/_doc/5
{
  "id": 5,
  "name": "八达岭长城",
  "pin": {
    "location": {
      "lat": 40.361375,
      "lon": 116.019809
    }
  }
}

Sort 返回距离

GET /scenic_spot/_search
{
  "query": {
    "match_all": {}
  },
  "sort": [
    {
      "_geo_distance": {
        "pin.location": {
          "lat": 38.912780578039346,
          "lon": 120.18819440815733
        },
        "order": "asc",
        "unit": "km"
      }
    }
  ],
  "size": 1
}

响应结果如下,hits 下的 sort 字段就是距离,单位:km。

{
  "took" : 4,
  "timed_out" : false,
  "_shards" : {
    "total" : 3,
    "successful" : 3,
    "skipped" : 0,
    "failed" : 0
  },
  "hits" : {
    "total" : {
      "value" : 5,
      "relation" : "eq"
    },
    "max_score" : null,
    "hits" : [
      {
        "_index" : "scenic_spot",
        "_type" : "_doc",
        "_id" : "3",
        "_score" : null,
        "_source" : {
          "id" : 3,
          "name" : "天坛公园",
          "pin" : {
            "location" : {
              "lat" : 39.881265,
              "lon" : 116.410638
            }
          }
        },
        "sort" : [
          341.96155623680716
        ]
      }
    ]
  }
}

Script_fields 返回距离

GET /scenic_spot/_search
{
  "query": {
    "match_all": {}
  },
  "_source": true,
  "script_fields": {
    "distance": {
      "script": {
        "lang": "painless",
        "params": {
          "lat": 38.912780578039346,
          "lon": 120.18819440815733
        },
        "source": "doc['pin.location'].arcDistance(params.lat, params.lon)/1000"
      }
    }
  },
  "size": 1
}

5.x 以前支持:distanceInKm(lat, lon) 函数,后来被废弃。现在只支持 arcDistance(lat, lon) 函数:计算两点距离,单位为:m。响应结果如下,hits 下的 fields.distance 字段就是距离,单位:km。

{
  "took" : 3,
  "timed_out" : false,
  "_shards" : {
    "total" : 3,
    "successful" : 3,
    "skipped" : 0,
    "failed" : 0
  },
  "hits" : {
    "total" : {
      "value" : 5,
      "relation" : "eq"
    },
    "max_score" : 1.0,
    "hits" : [
      {
        "_index" : "scenic_spot",
        "_type" : "_doc",
        "_id" : "5",
        "_score" : 1.0,
        "_source" : {
          "id" : 5,
          "name" : "八达岭长城",
          "pin" : {
            "location" : {
              "lat" : 40.361375,
              "lon" : 116.019809
            }
          }
        },
        "fields" : {
          "distance" : [
            391.55015001577397
          ]
        }
      }
    ]
  }
}

地理点和地理多边形范围查找

Elasticsearch](https://so.csdn.net/so/search?q=Elasticsearch&spm=1001.2101.3001.7020) 是一个功能强大的搜索引擎,支持地理查询,但并不是每个人都习惯于处理空间数据。 如果你对地理处理了解不多,或者想通过 Elasticsearch 了解地理处理,那么本文适合你。在我们的现实生活中,我们经常使用的滴滴打车,美团送餐,美国的 Uber, Lyft 打车,还有一些交友 apps 等等,它们都是使用 Elasticsearch 进行位置搜索的例子。

地理距离查询返回距离点最大距离的所有文档,例如:Dolores 想认识距离她约 300 米的所有人:

elasticsearch 计算距离,elasticsearch,搜索引擎,大数据

红色圆圈的半径为 300 米,我们可以看到只有 William 在圆圈内。

让我们来做一下 Elasticsearch 的实现。 首先,使用属性 name 和 location 创建一个 user_location 索引。

PUT user_location
{
  "mappings": {
    "properties": {
      "name": {
        "type": "text"
      },
      "location": {
        "type": "geo_point"
      }
    }
  }
}

location 的数据类型为 geo_point, 表示地球上的位置。 点具有经度和纬度(坐标)。 你可以在官方文档中检查所有可接受的 geo_point 格式。

现在,让我们为 William,Robert 和 Bernard 的位置创建文档。我们使用 _bulk API 来导入数据:

POST user_location/_bulk
{ "index" : { "_id" : "1" } }
{ "name" : "William", "location": "-25.443053, -49.238396" }
{ "index" : { "_id" : "2" } }
{ "name" : "Robert", "location": "-25.440173, -49.243169" }
{ "index" : { "_id" : "3" } }
{ "name" : "Bernard", "location": "-25.440262, -49.247720" }

为了说明问题的方便,我特地创建一个新的索引叫做 locations,它包含了 Dolores 的位置信息:

PUT locations
{
  "mappings": {
    "properties": {
      "name": {
        "type": "text"
      },
      "location": {
        "type": "geo_point"
      }
    }
  }
}
POST locations/_bulk
{ "index" : { "_id" : "1" } }
{ "name" : "William", "location": "-25.443053, -49.238396" }
{ "index" : { "_id" : "2" } }
{ "name" : "Robert", "location": "-25.440173, -49.243169" }
{ "index" : { "_id" : "3" } }
{ "name" : "Bernard", "location": "-25.440262, -49.247720" }
{ "index" : { "_id" : "4" } }
{ "name" : "Dolores", "location": "-25.442987, -49.239504" }

在上面的 _id 为 4 的文档就是 Doloes 的位置信息。我们来创建一个叫做 locations 的索引模式:

elasticsearch 计算距离,elasticsearch,搜索引擎,大数据

我们打开 Maps 应用:

elasticsearch 计算距离,elasticsearch,搜索引擎,大数据

elasticsearch 计算距离,elasticsearch,搜索引擎,大数据

elasticsearch 计算距离,elasticsearch,搜索引擎,大数据

elasticsearch 计算距离,elasticsearch,搜索引擎,大数据

elasticsearch 计算距离,elasticsearch,搜索引擎,大数据

elasticsearch 计算距离,elasticsearch,搜索引擎,大数据

我们发现这四个位置位于南美的某个地方。我们编辑 location 层的设置,当我们点击该位置的时候,显示名字及 id。我们调整合适的 zoom 大小:

elasticsearch 计算距离,elasticsearch,搜索引擎,大数据

elasticsearch 计算距离,elasticsearch,搜索引擎,大数据

从上面的图中,我们很清楚地看到每个人的相对的位置。离 Dolores 最近的就是 Willam,也就是那个被盖着的那个,接着就是 Robert。最远的就是 Bernard。请注意,我们上面的展示都是以 locations 这个索引来进行展示的。它里面含有 Dolores。我们现在使用 user_location 索引来进行搜索:

GET user_location/_search
{
  "query": {
    "bool": {
      "filter": {
        "geo_distance": {
          "distance": "300m",
          "location": "-25.442987, -49.239504"
        }
      }
    }
  }
}

在上面,我们针对 Dolores 来进行搜索。显示的结果是:

{
  "took" : 55,
  "timed_out" : false,
  "_shards" : {
    "total" : 1,
    "successful" : 1,
    "skipped" : 0,
    "failed" : 0
  },
  "hits" : {
    "total" : {
      "value" : 1,
      "relation" : "eq"
    },
    "max_score" : 0.0,
    "hits" : [
      {
        "_index" : "user_location",
        "_type" : "_doc",
        "_id" : "1",
        "_score" : 0.0,
        "_source" : {
          "name" : "William",
          "location" : "-25.443053, -49.238396"
        }
      }
    ]
  }
}

也就是说在 Dolores 方圆 300m 之内,只有 William。如果我们把半径增加到 600 m,那么我可以看到 Robert:

elasticsearch 计算距离,elasticsearch,搜索引擎,大数据

GET user_location/_search
{
  "query": {
    "bool": {
      "filter": {
        "geo_distance": {
          "distance": "600m",
          "location": "-25.442987, -49.239504"
        }
      }
    }
  }
}
{
  "took" : 2,
  "timed_out" : false,
  "_shards" : {
    "total" : 1,
    "successful" : 1,
    "skipped" : 0,
    "failed" : 0
  },
  "hits" : {
    "total" : {
      "value" : 2,
      "relation" : "eq"
    },
    "max_score" : 0.0,
    "hits" : [
      {
        "_index" : "user_location",
        "_type" : "_doc",
        "_id" : "1",
        "_score" : 0.0,
        "_source" : {
          "name" : "William",
          "location" : "-25.443053, -49.238396"
        }
      },
      {
        "_index" : "user_location",
        "_type" : "_doc",
        "_id" : "2",
        "_score" : 0.0,
        "_source" : {
          "name" : "Robert",
          "location" : "-25.440173, -49.243169"
        }
      }
    ]
  }
}

地理多边形查询可获取多边形内的文档。

“多边形是具有直边的封闭形状。 矩形,三角形,六边形和八边形都是多边形的例子。”

它由点列表表示。 两点之间最接近的路径是一条直线。 多边形的起点和终点均相同。 在下面的图上检查下面的植物园多边形。

elasticsearch 计算距离,elasticsearch,搜索引擎,大数据

请注意,Elasticsearch 上的地理查询会检查文档的 geo_point 属性是否在多边形内。 例:Dolores 想知道植物园内的每个人。

elasticsearch 计算距离,elasticsearch,搜索引擎,大数据

GET user_location/_search
{
  "query": {
    "bool": {
      "filter": {
        "geo_polygon": {
          "location": {
            "points": [
              "-25.44373,-49.24248",
              "-25.44297,-49.24230",
              "-25.44177,-49.23642",
              "-25.43961,-49.23822",
              "-25.43991,-49.23781",
              "-25.44170,-49.23647",
              "-25.44210,-49.23586",
              "-25.44218,-49.23506",
              "-25.44358,-49.23491",
              "-25.44406,-49.24139",
              "-25.44373,-49.24248"
            ]
          }
        }
      }
    }
  }
}

上面的搜索返回的结果:文章来源地址https://www.toymoban.com/news/detail-705978.html

{
  "took" : 15,
  "timed_out" : false,
  "_shards" : {
    "total" : 1,
    "successful" : 1,
    "skipped" : 0,
    "failed" : 0
  },
  "hits" : {
    "total" : {
      "value" : 1,
      "relation" : "eq"
    },
    "max_score" : 0.0,
    "hits" : [
      {
        "_index" : "user_location",
        "_type" : "_doc",
        "_id" : "1",
        "_score" : 0.0,
        "_source" : {
          "name" : "William",
          "location" : "-25.443053, -49.238396"
        }
      }
    ]
  }
}

到了这里,关于Elasticsearch计算距离,根据距离排序,地理点和地理多边形范围查找的文章就介绍完了。如果您还想了解更多内容,请在右上角搜索TOY模板网以前的文章或继续浏览下面的相关文章,希望大家以后多多支持TOY模板网!

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处: 如若内容造成侵权/违法违规/事实不符,请点击违法举报进行投诉反馈,一经查实,立即删除!

领支付宝红包 赞助服务器费用

相关文章

  • 根据经纬度计算两点之间的距离

    前言 在我们平时使用美团,饿了么等app进行订餐,或者使用猫眼进行订电影票的时候,都有一个距离的排序,表明该家店距离我们当前的位置,这种基于地理位置的服务,统一被称为LBS(Location Based Service),而LBS的实现则是借助于GIS,WC(无线通信)等信息技术来实现。而今

    2024年02月05日
    浏览(88)
  • 根据经纬度计算地球上两点之间的距离——Haversine公式介绍及计算步骤

    目录 摘要 1.半正矢公式(Haversine Formula)介绍 2.半正矢公式应用 3.半正矢公式计算 3.1 主要思路 3.2 计算步骤 3.2.1 平面向量计算方法 3.2.2 空间向量计算方法 写本文的出发点是需要在Qlik中根据经纬度计算地球上两点间的距离。我在社区上搜到了相关公式的分享,这个公式叫做

    2023年04月10日
    浏览(51)
  • ElasticSearch DSL语句(bool查询、算分控制、地理查询、排序、分页、高亮等)

    查询所有:查询所有数据,一般在测试时使用。march_all,但是一般显示全部,有一个分页的功能 全文检索(full text)查询:利用分词器对用户的输入内容进行分词,然后去倒排索引库匹配。例如: match_query mutil_match_query 精确查询:根据精确词条值查询数据,一般查找的时k

    2024年02月12日
    浏览(52)
  • Elasticsearch 地理空间计算

      地理位1置搜索:使用查询API进行搜索 1、Geo Distance Query Geo Distance Query是在给定的距离范围内搜索数据的查询。例如,可以搜索给定地理位置附近指定距离内的所有文档。 2、 Geo Bounding Box Query Geo Bounding Box Query是一种以四边形形式搜索地理坐标数据的查询。它可以定义顶点

    2024年02月12日
    浏览(56)
  • ElasticSearch如何使用以及java代码如何查询并排序ES中的数据(距离排序)

    import org.elasticsearch.client.RestHighLevelClient; import org.elasticsearch.client.transport.TransportClient; import org.elasticsearch.common.geo.GeoDistance; import org.elasticsearch.common.settings.Settings; import org.elasticsearch.common.transport.TransportAddress; import org.elasticsearch.common.unit.DistanceUnit; import org.elasticsearch.common.unit.

    2024年04月12日
    浏览(50)
  • uniapp微信小程序,根据用户当前位置计算用户到附近机构/商店的距离

    1、首先要弄清楚后端传过来的经纬度是属于哪一类,一共有三大类,分别是:WGS84,GCJ02,BD09 WGS84:为一种大地坐标系,也是目前广泛使用的GPS全球卫星定位系统使用的坐标系。 GCJ02:又称火星坐标系,是由中国国家测绘局制定的地理坐标系统,是由WGS84加密后得到的坐标系

    2024年02月15日
    浏览(48)
  • 空间分析实战指南:点到多边形的最短距离

    在我们最近的项目中,出现了一个新的需求:需要验证现场拍摄的照片的经纬度与实际地块之间的最短距离,以确保业务员在地块的一公里范围内进行拍照。 实现这个功能有两种方式,一种是在前台APP中校验,一种是在后台进行校验,接下来我会分别介绍这两种方式。 在我

    2024年02月13日
    浏览(38)
  • matlab做经济地理、地理距离、经济距离空间权重矩阵

    首先讲下地理加权空间权重矩阵: 该矩阵的经济含义是通过不同点的坐标系之间的距离远近来衡量两地之间的关系重要程度,当两点之间距离较远,所占的权重越低,而距离越近,权重越高。故操作如下: 首先需要导入坐标数据: A=csvread(\\\'JWD.csv\\\',1,0); % JWD.csv是文件名,csvrea

    2023年04月12日
    浏览(39)
  • 285个地级市空间权重矩阵(空间邻接、地理距离、经济距离、经济地理嵌套矩阵)

    285个地级市空间权重矩阵(空间邻接、地理距离、经济距离、经济地理嵌套矩阵) 1、范围:285个地级市 2、数据包括:包括空间邻接矩阵、空间地理距离矩阵、空间经济距离矩阵、空间经济地理嵌套矩阵 其中空间经济距离矩阵根据2003-2019年人均GDP得到 3、指标说明: 空间权

    2024年02月16日
    浏览(57)
  • mysql如何实现根据经纬度判断某一个坐标是否在一个多边形区域范围内

    要根据经纬度判断一个坐标是否在一个多边形区域内,MySQL提供了几种函数来处理地理空间数据,其中包括用于处理多边形区域的函数。 首先,创建一个表来存储多边形区域。可以使用 ST_GeomFromText 函数将多边形的坐标转换为地理空间对象。我们给他插入两条数据,默认id第一

    2024年02月08日
    浏览(57)

觉得文章有用就打赏一下文章作者

支付宝扫一扫打赏

博客赞助

微信扫一扫打赏

请作者喝杯咖啡吧~博客赞助

支付宝扫一扫领取红包,优惠每天领

二维码1

领取红包

二维码2

领红包