MST

星途 面试题库

面试题:分布式系统中基于TTL的缓存数据过期清理策略的实现方式

在分布式系统后端开发场景下,简述如何基于TTL(Time - To - Live)实现缓存数据的过期清理策略?请举例说明至少两种常见的实现思路。
23.2万 热度难度
后端开发分布式系统

知识考点

AI 面试

面试题答案

一键面试

思路一:在写入缓存时设置 TTL

  1. 原理:当向缓存中写入数据时,同时设置该数据的 TTL。缓存系统会在内部维护一个数据结构,记录每个数据项的过期时间。在每次读取数据时,先检查数据是否过期,如果过期则从缓存中删除,并返回空值或重新从数据源获取数据。
  2. 示例:在 Redis 中,可以使用 SET key value EX seconds 命令来设置键值对并指定过期时间(以秒为单位)。例如:
SET user:1 "John Doe" EX 3600  # 设置键 user:1 的值为 "John Doe",并在 3600 秒(1 小时)后过期

当执行 GET user:1 时,Redis 会检查该键是否过期,如果未过期则返回值;若已过期,返回空值,应用程序可以据此从数据库等数据源重新获取数据并更新缓存。

思路二:定期扫描缓存

  1. 原理:启动一个后台线程或定时任务,定期扫描缓存中的所有数据项,检查它们的过期时间。对于已过期的数据,从缓存中删除。这种方式不需要在每次读取数据时都检查过期时间,但可能会导致缓存中有少量过期数据在扫描周期内仍然存在。
  2. 示例:假设使用一个简单的 Python 字典模拟缓存,并使用 threading.Timer 来实现定期扫描。
import threading
import time

cache = {}

def set_cache(key, value, ttl):
    cache[key] = (value, time.time() + ttl)

def get_cache(key):
    if key in cache:
        value, expire_time = cache[key]
        if time.time() < expire_time:
            return value
        else:
            del cache[key]
    return None

def clean_cache():
    while True:
        current_time = time.time()
        keys_to_delete = []
        for key, (_, expire_time) in cache.items():
            if current_time > expire_time:
                keys_to_delete.append(key)
        for key in keys_to_delete:
            del cache[key]
        time.sleep(60)  # 每 60 秒扫描一次

# 启动清理线程
clean_thread = threading.Thread(target=clean_cache)
clean_thread.daemon = True
clean_thread.start()

# 设置缓存示例
set_cache('test_key', 'test_value', 30)  # 设置一个 30 秒过期的缓存