2021-04-26 02:13:30
Redis和Memcached作为缓存技术的核心区别体现在数据存储、数据类型、持久化、线程模型、内存管理、分布式方案及高级功能上,具体如下:
1. 数据存储与容量限制单条数据最大支持 512MB,适合存储大对象(如序列化后的JSON、图片二进制数据)。
数据以 Redis对象(redisObject) 形式存储,包含类型(type)、编码(encoding)、访问时间(lru)、引用计数(refcount)等元信息,支持灵活的内存回收和优化。
单条数据最大支持 1MB,仅适合存储小对象(如字符串、简单键值对)。
数据以 item 形式存储在 chunk 中,chunk由 slab 管理,内存分配固定,无元信息开销。
支持 5种核心数据类型:字符串(String)、哈希(Hash)、列表(List)、集合(Set)、有序集合(ZSet)。
扩展功能:位图(Bitmaps)、超日志(HyperLogLog)、地理空间索引(GEO)等,适用于复杂场景(如计数器、排行榜、范围查询)。
仅支持 简单键值对(String),数据结构单一,适合纯缓存场景(如会话存储、页面片段缓存)。
RDB(快照):定时生成数据快照,恢复速度快但可能丢失最后一次快照后的数据。
AOF(日志):记录所有写操作,支持重写(AOF Rewrite)减少文件体积,数据安全性高但恢复速度较慢。
推荐方案:综合使用RDB和AOF,以AOF为主保证数据不丢失,RDB为辅实现快速冷备。
不支持持久化,数据仅存储在内存中,重启后数据丢失,适合对数据持久性要求低的场景(如临时缓存)。
单线程I/O多路复用:基于事件轮询(select/epoll/kqueue)处理请求,避免线程切换开销,但单核CPU利用率受限。
优势:无锁竞争,适合高并发读写(如每秒10万+请求)。
多线程I/O多路复用:主线程监听连接,子线程(worker)处理读写,利用多核CPU提升吞吐量。
劣势:全局锁(如stats命令)导致性能损耗,高并发下锁竞争明显。
动态内存分配:基于包装的malloc/free(如zmalloc.h),记录内存块大小和分配情况,可能产生碎片。
优化策略:通过内存回收(如LRU)和编码优化(如压缩列表、整数集合)减少碎片。
Slab Allocation:预先分配固定大小的内存块(slab class),每个slab包含多个chunk,数据按chunk存储。
优势:无内存碎片,但可能浪费空间(如小对象占用大chunk)。
淘汰策略:LRU算法回收冷数据,支持懒淘汰(lazy expiration)在访问时检查过期。
集群模式:
Redis Cluster:基于哈希槽(16384个槽)分配数据,支持动态扩容和故障转移。
哨兵(Sentinel):监控主从节点,自动故障切换,但扩容复杂。
客户端方案:通过代理(如Twemproxy、Codis)或智能客户端实现分片。
一致性哈希:通过虚拟节点均匀分布数据,避免雪崩效应。
代理实现:如memagent,支持客户端分片和负载均衡。
事务支持:通过MULTI/EXEC保证命令原子性,但不支持回滚。
Lua脚本:允许原子化执行复杂逻辑。
发布/订阅:支持消息通信模式。
CAS命令:通过版本号(CAS token)实现乐观锁,解决并发更新问题。
无事务和脚本支持,功能简单。
需要持久化、复杂数据结构、高可用集群的场景(如电商库存、实时排行榜)。
适合数据量大、对安全性要求高的业务(如金融交易、会话管理)。
纯内存缓存、简单键值对、高吞吐量场景(如CDN内容缓存、广告点击计数)。
适合对数据持久性无要求、追求极致性能的业务(如实时日志处理)。