94. 熟悉Redis吗,项目中你是如何对Redis内存进行优化的(二)
三、redis 子进程内存消耗
子进程即redis执行持久化(RDB/AOF)时fork的子任务进程。
1、关于linux系统的写时复制机制:
父子进程会共享相同的物理内存页,父进程处理写请求时会对需要修改的页复制一份副本进行修改,子进程读取的内存则为fork时的父进程内存快照,因此,子进程的内存消耗由期间的写操作增量决定。
2、关于linux的透明大页机制THP(Transparent Huge Page):
THP机制会降低fork子进程的速度;写时复制内存页由4KB增大至2M。高并发情境下,写时复制内存占用消耗影响会很大,因此需要选择性关闭。
3、关于linux配置:
一般需要配置linux系统 vm.overcommit_memory=1,以允许系统可以分配所有的物理内存。防止fork任务因内存而失败。
四、redis 内存管理
redis的内存管理主要分为两方面:内存上限控制及内存回收管理。
1、内存上限:maxmemory
目的:缓存应用内存回收机制触发 + 防止物理内存用尽(redis 默认无限使用服务器内存) + 服务节点内存隔离(单服务器上部署多个redis服务节点)
在进行内存分配及限制时要充分考虑内存碎片占用影响。
动态调整,扩展redis服务节点可用内存:config set maxmemory {}。
2、内存回收
回收时机:键过期、内存占用达到上限
1、过期键删除:
redis 键过期时间保存在内部的过期字典中,redis采用惰性删除机制+定时任务删除机制。
**惰性删除:**即读时删除,读取带有超时属性的键时,如果键已过期,则删除然后返回空值。这种方式存在问题是,触发时机,加入过期键长时间未被读取,那么它将会一直存在内存中,造成内存泄漏。
**定时任务删除:**redis内部维护了一个定时任务(默认每秒10次,可配置),通过自适应法进行删除。
删除逻辑如下:
需要说明的一点是,快慢模式执行的删除逻辑相同,这是超时时间不同。
2、内存溢出控制
当内存达到maxmemory,会触发内存回收策略,具体策略依据maxmemory-policy来执行。
noevication:默认不回收,达到内存上限,则不再接受写操作,并返回错误。
volatile-lru:根据LRU算法删除设置了过期时间的键,如果没有则不执行回收。
allkeys-lru:根据LRU算法删除键,针对所有键。
allkeys-random:随机删除键。
volatitle-random:速记删除设置了过期时间的键。
volatilte-ttl:根据键ttl,删除最近过期的键,同样如果没有设置过期的键,则不执行删除。
动态配置:config set maxmemory-policy {}
在设置了maxmemory情况下,每次的redis操作都会检查执行内存回收,因此对于线上环境,要确保所这只的maxmemory>used_memory。
另外,可以通过动态配置maxmemory来主动触发内存回收。
动态配置:config set maxmemory-policy {}
在设置了maxmemory情况下,每次的redis操作都会检查执行内存回收,因此对于线上环境,要确保所这只的maxmemory>used_memory。
另外,可以通过动态配置maxmemory来主动触发内存回收。