本文共 1695 字,大约阅读时间需要 5 分钟。
简介
- 官网:
- Github: 一款高性能,分布式内存对象缓存系统。
使用目的
缓存数据查询结果,减少数据库访问次数,以提高Web应用的响应速度、提高可扩展性。
特点
- 互不通信的分布式方式,服务端自身不提供实现,由客户端实现
- 内置内存存储机制,不支持数据持久、数据同步
- 仅支持Key-Value数据结构
- 支持多线程,基于LibEvent事件处理(参考:
内存分配机制(Slab Allocation)
- Chunk:Memcached中存放数据的最小单元(Key、Value)。
- Page:由多个相同大小的Chunk组成。固定大小,默认值为1M,可以通过启动参数
-I
设定。 - Slab :由多个相同大小的Page组成。
原理
- 启动Memcached时,立即分配
-m
参数设定大小的内存,并按Page的大小分割成多个Page。 - 当Slab申请内存时,将分配一个可用的Page,并按照Slab的Chunk大小分割成多个Chunk。
- 当数据被存储时,会分配到内存浪费最少的Slab中。
优点
缺点
- 内存浪费
- Slab中的每个Chunk大小是固定的,当存储的数据小于Chunk大小,则产生少量不可使用的内存
- Page的大小也是固定的,当分割成固定大小的Chunk时,可能剩余不足以分割的内存
- 按照Growth Factor因子生成指定大小的Slab,而某Slab的Id根本未被使用时,会出现内存浪费
调优
- Memcached 在启动时指定 Growth Factor 因子(
-f
),就可以在某种程度上控制 Slab 之间的 差异。默认值为 1.25。最佳值应该通过分析数据的平均长度而定
- Memcached 在启动时指定 Growth Factor 因子(
-f
),就可以在某种程度上控制 Slab 之间的 差异。默认值为 1.25。最佳值应该通过分析数据的平均长度而定
内存回收机制(LRU)
- 数据不会过期删除:Memcached 不会释放已分配的内存,存储空间利用LRU机制重复使用
- 缓存延迟失效机制:Memcached 不会主动监控缓存失效,而是使用Get时查看记录的时间戳,是否已过期。
- LRU缓存删除
- 优先使用已经超时的内存空间
- 当没有可使用的空间时,将查找最近未被使用的记录,并将空间直接分配给新的记录
分布式机制
- 再抛出上面的问题,如果新添加或移除一台机器,在consistent Hashing算法下会有什么影响。上图中假设有四个节点,我们再添加一个节点叫node5:
- node5被放在了node4与node2之间,本来映射到node2和node4之间的区域都会找到node4,当有node5的时候,node5和node4之间的还是找到node4,而node5和node2之间的此时会找到node5,因此当添加一台服务器的时候受影响的仅仅是node5和node2区间。
缓存命中率
命中率 = get成功次数 / get总次数
命中率越高意味着访问数据库的次数越少,带来的性能提升也是最大的。
注意事项
- 使用缓存一定是读多写少,实时性较高的数据不适用缓存
- Page默认值为1MB,所以数据大小受限于Page大小,处理方案:
- 数据分片存储,降低单个Chunk大小
- 利用客户端实现gzip压缩数据
- Page默认值调高,但可能导致内存浪费率增高,需具体分析后处理,建议作为最终办法
参考文献
转载地址:http://omhnn.baihongyu.com/