PHP+Redis查询附近的人功能

在之前的博客《MySQL 查询附近的人》中,使用 MySQL 查询附近的人在用户较少时性能表现尚可。然而,随着应用用户的增多,查询性能问题开始凸显。因此,这篇文章介绍了使用 Redis 的 GEO 数据类型来提升查询效率,特别是在 Redis 6.0 中,这些功能得到了增强,我测试环境使用的是7.2,如果你的版本不支持,请尽可能的使用新版的Redis。

Redis 的 GEO 数据类型从 Redis 3.2 版本开始引入,主要用于存储和操作地理位置信息。通过 Redis 的 GEO 功能,可以快速实现类似“查询附近的人”等地理位置相关的功能。

Redis GEO 操作方法

Redis 提供了一系列用于操作地理位置信息的命令,常用的有:

  • geoadd:向指定的 key 添加地理位置的坐标(经度、纬度)。
  • geopos:获取某个地理位置的坐标。
  • geodist:计算两个位置之间的距离。
  • georadius:根据给定的经纬度坐标,获取指定范围内的地理位置集合。
  • georadiusbymember:根据已存储的位置的成员名,获取该地点附近的地理位置集合。
  • geohash:返回位置对象的 geohash 值(用于调试或底层应用)。

开始使用

1. 连接 Redis

首先需要连接到 Redis 服务器。在 Redis 6.0 之后,如果启用了密码或 ACL(访问控制列表),需要通过身份认证登录。

$redis = new Redis();
$redis->connect('127.0.0.1', 6379);

// 如果 Redis 设置了密码或启用了 ACL,可以这样进行认证
// $redis->auth(['user' => 'default', 'pass' => 'password']);

2. 记录用户地理位置信息

我们通过 geoadd 命令来记录用户的位置信息(经度、纬度)。这里用 user:member 作为成员标识。

$redis->geoAdd("KEY", longitude, latitude, "member:1");
$redis->geoAdd("KEY", longitude, latitude, "member:2");

geoadd 语法说明

GEOADD key longitude latitude member [longitude latitude member ...]

该命令将一个或多个地理位置的经纬度和成员名存储到指定的 key 中。

3. 查询附近的人

假设我们想查找某个坐标点附近 10 公里范围内的最多 100 个人,并按距离从近到远排序,可以使用 georadius 命令。

$options = ['WITHDIST', 'COUNT' => 100, 'ASC'];
$lists = $redis->geoRadius('KEY', longitude, latitude, 10, 'km', $options);

georadius 语法说明

GEORADIUS key longitude latitude radius m|km|ft|mi [WITHCOORD] [WITHDIST] [WITHHASH] [COUNT count] [ASC|DESC] [STORE key] [STOREDIST key]
  • m:单位为米,默认单位。
  • km:单位为千米。
  • mi:单位为英里。
  • ft:单位为英尺。
  • WITHDIST:返回结果中包含距离信息。
  • WITHCOORD:返回结果中包含经纬度信息。
  • COUNT:限定返回的记录数量。
  • ASC:根据距离从近到远排序。
  • DESC:根据距离从远到近排序。

4. 查询两个用户之间的距离

如果需要查询两个用户(成员)之间的距离,可以使用 geodist 命令。例如,查询 member1member2 之间的距离:

$result = $redis->geoDist('KEY', 'member:1', 'member:2', 'km');

geodist 语法说明

GEODIST key member1 member2 [m|km|ft|mi]

此命令会返回两个位置之间的距离,支持多种单位(米、千米、英里、英尺)。

标签: PHP, Redis

相关文章

如何在PHP框架Workerman中实现异步任务处理

在现代Web应用中,处理繁重的业务逻辑时,避免主业务流程被长时间阻塞是非常重要的。Workerman是一个高性能的PHP Socket框架,支持异步任务处理,可以有效地解决这一问题。本文将详细介...

PHP中使用CURL下载远程超大文件的方法

在使用PHP进行开发时,我们经常需要从远程服务器下载文件。当文件体积较大时,普通的文件操作和cURL方法可能会因为内存限制或执行时间限制而失败。本文将介绍如何使用PHP中的cURL扩展来高效地下...

PHP命名空间使用详解

在 PHP 中,命名空间(Namespace)是一种将相关的类、函数和常量组织到一个逻辑分组中的方式。它有助于避免命名冲突,并提高代码的可维护性和可扩展性。一、命名空间的定义使用 namespa...

复习一下PHP中的类和对象

面向对象编程(OOP)是一种编程范式,它通过类和对象的概念来组织代码。PHP 作为一种广泛使用的服务器端脚本语言,从 PHP 5 开始就全面支持面向对象编程。本文将深入探讨 PHP 中类和对象的...

图片Base64编码

CSR生成

图片无损放大

图片占位符

Excel拆分文件