Redis - 列表
Redis - 列表(Lists)
Section titled “Redis - 列表(Lists)”Redis 列表是字符串的有序集合,按插入顺序排序。它们被实现为链表(Linked Lists),这使得即使对于包含数百万元素的列表,向列表的头部(左侧)或尾部(右侧)添加新元素也速度非常快。
像 LPUSH(添加到头部)和 RPOP(从尾部移除)这样的关键操作是 O(1),这意味着它们的速度与列表的大小无关。列表的最大长度为 2^32 - 1 个元素(超过 40 亿)。
实际示例:一个简单的任务队列
Section titled “实际示例:一个简单的任务队列”列表非常适合实现生产者-消费者模式,例如任务队列。一个“生产者”(producer)应用程序将任务推送到列表中,一个或多个“工作者”(worker)应用程序从列表中拉取任务进行处理。
生产者:推送任务
Section titled “生产者:推送任务”生产者使用 LPUSH 将新任务添加到名为 task_queue 的列表头部。我们将使用 JSON 字符串来表示结构化任务。
# Producer adds three tasks to the queue# 生产者向队列添加三个任务redis> LPUSH task_queue '{"type":"send_email", "recipient":"user1@example.com"}'(integer) 1redis> LPUSH task_queue '{"type":"generate_report", "report_id":"xyz-123"}'(integer) 2redis> LPUSH task_queue '{"type":"process_image", "image_id":987}'(integer) 3工作者:处理任务
Section titled “工作者:处理任务”工作者可以使用 RPOP 从列表的尾部获取最旧的任务。然而,一个更好的方法是使用阻塞命令 BRPOP。它原子性地移除并返回最后一个元素,但如果列表为空,它将阻塞连接,直到有新元素可用或达到超时。这比不断轮询列表效率高得多。
# Worker asks for a task, blocking for up to 10 seconds if none are available.# 工作者请求一个任务,如果没有可用任务则阻塞最长 10 秒。# It receives the first task that was pushed (FIFO - First-In, First-Out).# 它接收第一个被推送的任务(FIFO - 先进先出)。redis> BRPOP task_queue 101) "task_queue"2) "{\"type\":\"send_email\", \"recipient\":\"user1@example.com\"}"
# Worker asks again and gets the next task# 工作者再次请求并获得下一个任务redis> BRPOP task_queue 101) "task_queue"2) "{\"type\":\"generate_report\", \"report_id\":\"xyz-123\"}"
# If the worker asks again and the queue is empty, the command will wait.# 如果工作者再次请求且队列为空,命令将等待。# After 10 seconds, if no producer has pushed a new task, it will return (nil).# 10 秒后,如果没有生产者推送新任务,它将返回 (nil)。redis> BRPOP task_queue 10(nil)(10.00s)最佳实践和主要考虑事项
Section titled “最佳实践和主要考虑事项”- 有上限的列表(Capped Lists):对于存储最新日志或活动等用例,使用
LPUSH添加项目,并使用LTRIM定期将列表裁剪到固定大小。这可以防止无限制的内存增长。 - 避免列表中间操作:像
LINDEX(按索引获取元素)和LINSERT(按索引插入元素)这样的命令速度较慢(O(N))。它们需要从列表头部或尾部遍历列表。对于高性能应用程序,请坚持使用头部/尾部操作(LPUSH、RPUSH、LPOP、RPOP)。 - 对于可靠队列,考虑 Streams:虽然列表非常适合简单的队列,但它们缺乏消息确认和消费者组等功能。如果你不能承受丢失单个任务的风险(例如,如果工作者在
RPOP之后但在完成之前崩溃),则应使用更强大的 Redis Streams 数据结构。
常用列表命令
Section titled “常用列表命令”| 命令 | 描述 |
|---|---|
| LPUSH key element [element …] | 将一个或多个元素前置到列表的头部(左侧)。 |
| RPUSH key element [element …] | 将一个或多个元素追加到列表的尾部(右侧)。 |
| LPOP key [count] | 移除并返回列表的第一个元素(从头部)。 |
| RPOP key [count] | 移除并返回列表的最后一个元素(从尾部)。 |
| BLPOP key [key …] timeout | LPOP 的阻塞版本。阻塞直到有元素可用或超时发生。 |
| BRPOP key [key …] timeout | RPOP 的阻塞版本。可靠工作者队列的首选命令。 |
| LLEN key | 获取列表的长度。 |
| LRANGE key start stop | 从列表中获取一个元素范围。在非常长的列表上使用时要谨慎。 |
| LTRIM key start stop | 将列表裁剪到指定的范围,移除范围之外的元素。 |