Redis

关注公众号 jb51net

关闭
首页 > 数据库 > Redis > Redis GEO

Redis中的GEO详解

作者:悟能不能悟

Redis GEO是一个轻量级的地理位置解决方案,适合需要快速存储和查询位置数据的场景,本文给大家介绍Redis的GEO详解,感兴趣的朋友一起看看吧

Redis GEO

Redis GEO 主要用于存储地理位置信息,并对存储的信息进行操作,该功能在 Redis 3.2 版本新增。

Redis GEO 操作方法有:

Redis 的 GEO(Geographic)模块是用于处理地理位置信息的工具集,主要支持存储地理位置数据计算位置间距离查询指定范围内的位置等功能。其底层基于有序集合(ZSET)实现,利用了 ZSET 的排序特性来管理地理位置的排序和查询。以下从核心原理、常用命令、应用场景及注意事项等方面详细说明:

​一、核心原理:基于 Geohash 和 ZSET​

Redis GEO 的底层数据结构是 ​ZSET(有序集合)​,每个地理位置的成员(member)在 ZSET 中存储为:

​Geohash 算法​

Geohash 是一种将二维经纬度(latitude, longitude)编码为一维字符串的算法。其核心思想是通过二分法将经纬度分别划分为网格,最终生成一个由数字和字母组成的短字符串(长度越短,精度越低,覆盖范围越大)。例如:

Redis 利用 Geohash 的这一特性,将地理位置存储为 ZSET 的分数(score),从而借助 ZSET 的有序性实现高效的距离计算和范围查询。

​二、常用命令详解​

Redis GEO 提供了一系列命令,用于位置管理、距离计算和范围查询。以下是最核心的命令:

​1. GEOADD:添加/更新地理位置​

语法​:
GEOADD key longitude latitude member [longitude latitude member ...]

功能​:向 key 中添加一个或多个地理位置(若成员已存在,则更新其经纬度)。

示例​:

# 添加北京天安门(经度116.405285,纬度39.904989)和上海东方明珠(经度121.473701,纬度31.230416)
GEOADD stores 116.405285 39.904989 "天安门" 121.473701 31.230416 "东方明珠"

返回值​:成功添加的新成员数量(重复成员不计入)。

​2. GEODIST:计算两个位置的距离​

语法​:
GEODIST key member1 member2 [unit]

功能​:计算 member1 和 member2 之间的直线距离。

示例​:

# 计算天安门到东方明珠的距离(千米)
GEODIST stores "天安门" "东方明珠" km
# 输出:约 1067.4702 km(实际计算值可能因精度略有差异)

注意​:若任一成员不存在,返回 nil

​3. GEORADIUS:查询指定中心点附近的成员​

语法​:
GEORADIUS key longitude latitude radius unit [WITHCOORD] [WITHDIST] [WITHHASH] [COUNT n] [ASC|DESC]

功能​:以给定的经纬度为中心,查询半径范围内的所有成员,并可选返回额外信息。

示例​:

# 查询天安门(116.405285, 39.904989)周围 2 公里内的店铺,返回距离和坐标
GEORADIUS stores 116.405285 39.904989 2 km WITHDIST WITHCOORD

返回值​(示例):

1) 1) "天安门"          # 成员名
   2) "0.0000"         # 到中心点的距离(km)
   3) 1) "116.405285"  # 经度
      2) "39.904989"   # 纬度

​4. GEORADIUSBYMEMBER:以成员为中心查询附近​

语法​:
GEORADIUSBYMEMBER key member radius unit [WITHCOORD] [WITHDIST] [WITHHASH] [COUNT n] [ASC|DESC]

功能​:与 GEORADIUS 类似,但中心点由已有成员的位置决定(无需手动输入经纬度)。

示例​:

# 查询以“天安门”为中心,周围 5 公里的店铺
GEORADIUSBYMEMBER stores "天安门" 5 km WITHDIST

​5. GEOHASH:获取成员的 Geohash 编码​

语法​:
GEOHASH key member [member ...]

功能​:返回一个或多个成员的 Geohash 字符串(基于 ZSET 的分数转换而来)。

示例​:

# 获取“天安门”的 Geohash
GEOHASH stores "天安门"
# 输出:"wx4g0s8q3jf9"(实际值可能因 Redis 版本略有差异)

应用场景​:通过比较 Geohash 前缀快速判断位置的相似性(前缀越长,位置越接近)。

​6. GEORADIUSBYMEMBER_RO / GEORADIUS_RO:只读查询(Redis 3.2.10+)​​

为了支持集群模式下的只读操作,Redis 提供了 GEORADIUSBYMEMBER_RO(基于成员)和 GEORADIUS_RO(基于经纬度)命令,避免在集群环境中因重定向导致的性能问题。

​三、关键注意事项​

​四、典型应用场景​

附近的人/店铺​:如外卖 App 查询用户附近的餐厅,社交 App 查找附近的好友。

# 用户当前位置(经度121.475,纬度31.230),查询 3 公里内的餐厅
GEORADIUS restaurants 121.475 31.230 3 km WITHDIST

​五、总结​

Redis GEO 是一个轻量级的地理位置解决方案,适合需要快速存储和查询位置数据的场景。其核心优势是利用 ZSET 的有序性实现了高效的距离计算和范围查询,但也需注意经纬度顺序、数据删除方式和性能限制。实际使用中,需根据业务需求选择合适的命令(如 GEORADIUS 或 GEORADIUSBYMEMBER),并结合 WITH* 参数优化返回结果。

到此这篇关于Redis中的GEO详解的文章就介绍到这了,更多相关Redis GEO内容请搜索脚本之家以前的文章或继续浏览下面的相关文章希望大家以后多多支持脚本之家!

您可能感兴趣的文章:
阅读全文