`
longzhun
  • 浏览: 360976 次
  • 性别: Icon_minigender_1
  • 来自: 北京
社区版块
存档分类
最新评论

九.redis学习笔记之虚拟内存

 
阅读更多

首先说明下redis的虚拟内存与os的虚拟内存不是一码事,但是思路和目的都是相同的。就是暂时把不经常访问的数据从内存交换到磁盘中,从而腾出宝贵的 内存空间用于其他需要访问的数据。尤其是对于redis这样的内存数据库,内存总是不够用的。除了可以将数据分割到多个redis server外。另外的能够提高数据库容量的办法就是使用vm把那些不经常访问的数据交换的磁盘上。如果我们的存储的数据总是有少部分数据被经常访问,大 部分数据很少被访问,对于网站来说确实总是只有少量用户经常活跃。当少量数据被经常访问时,使用vm不但能提高单台redis server数据库的容量,而且也不会对性能造成太多影响。
        redis没有使用os提供的虚拟内存机制而是自己在用户态实现了自己的虚拟内存机制,作者在自己的blog专门解释了其中原因。http://antirez.com/post/redis-virtual-memory-story.html
主要的理由有两点
1.os 的虚拟内存是已4k页面为最小单位进行交换的。而redis的大多数对象都远小于4k,所以一个os页面上可能有多个redis对象。另外redis的集 合对象类型如list,set可能存在与多个os页面上。最终可能造成只有10%key被经常访问,但是所有os页面都会被os认为是活跃的,这样只有内 存真正耗尽时os才会交换页面。
2.相比于os的交换方式。redis可以将被交换到磁盘的对象进行压缩,保存到磁盘的对象可以去除指针和对象元数据信息。一般压缩后的对象会比内存中的对象小10倍。这样redis的vm会比os vm能少做很多io操作。
下面是vm相关配置
vm-enabled yes                          #开启vm功能
vm-swap-file /tmp/redis.swap                 #交换出来的value保存的文件路径/tmp/redis.swap
vm-max-memory 1000000                    #redis使用的最大内存上限,超过上限后redis开始交换value到磁盘文件中。
vm-page-size 32                    #每个页面的大小32个字节
vm-pages 134217728                 #最多使用在文件中使用多少页面,交换文件的大小 = vm-page-size * vm-pages
vm-max-threads 4                    #用于执行value对象换入换出的工作线程数量。0表示不使用工作线程(后面介绍)
       redis的vm在设计上为了保证key的查找速度,只会将value交换到swap文件中。所以如果是内存问题是由于太多value很小的key造成 的,那么vm并不能解决。和os一样redis也是按页面来交换对象的。redis规定同一个页面只能保存一个对象。但是一个对象可以保存在多个页面中。 在redis使用的内存没超过vm-max-memory之前是不会交换任何value的。当超过最大内存限制后,redis会选择较老的对象。如果两个 对象一样老会优先交换比较大的对象,精确的公式swappability = age*log(size_in_memory)。 对于vm-page-size的设置应该根据自己的应用将页面的大小设置为可以容纳大多数对象的大小。太大了会浪费磁盘空间,太小了会造成交换文件出现碎 片。对于交换文件中的每个页面,redis会在内存中对应一个1bit值来记录页面的空闲状态。所以像上面配置中页面数量(vm-pages 134217728 )会占用16M内存用来记录页面空闲状态。vm-max-threads表示用做交换任务的线程数量。如果大于0推荐设为服务器的cpu core的数量。如果是0则交换过程在主线程进行。
参数配置讨论完后,在来简单介绍下vm是如何工作的,
当vm-max-threads设为0时(Blocking VM)
换出
主线程定期检查发现内存超出最大上限后,会直接已阻塞的方式,将选中的对象保存到swap文件中,并释放对象占用的内存,此过程会一直重复直到下面条件满足
1.内存使用降到最大限制以下
2.swap文件满了
3.几乎全部的对象都被交换到磁盘了
换入
当有client请求value被换出的key时。主线程会以阻塞的方式从文件中加载对应的value对象,加载时此时会阻塞所以client。然后处理client的请求
当vm-max-threads大于0(Threaded VM)
换出
当主线程检测到使用内存超过最大上限,会将选中的要交换的对象信息放到一个队列中交由工作线程后台处理,主线程会继续处理client请求。
换入
如果有client请求的key被换出了,主线程先阻塞发出命令的client,然后将加载对象的信息放到一个队列中,让工作线程去加载。加载完毕后工作线程通知主线程。主线程再执行client的命令。这种方式只阻塞请求value被换出key的client
总 的来说blocking vm的方式总的性能会好一些,因为不需要线程同步,创建线程和恢复被阻塞的client等开销。但是也相应的牺牲了响应性。threaded vm的方式主线程不会阻塞在磁盘io上,所以响应性更好。如果我们的应用不太经常发生换入换出,而且也不太在意有点延迟的话则推荐使用blocking vm的方式。关于redis vm的更详细介绍可以参考下面链接
http://antirez.com/post/redis-virtual-memory-story.html
http://redis.io/topics/internals-vm

from:http://www.cnblogs.com/xhan/archive/2011/02/07/1949717.html

分享到:
评论

相关推荐

    1.2.6版StackExchange.Redis

    把下载的三个文件(StackExchange.Redis.dll、StackExchange.Redis.dll.refresh、StackExchange.Redis.xml)复制粘贴到计算机上的某个目录下。然后在vs2010的解决方案资源管理器窗口中右击项目,单击“添加引用”,...

    1.2.1版StackExchange.Redis

    把下载的三个文件(StackExchange.Redis.dll、StackExchange.Redis.dll.refresh、StackExchange.Redis.xml)复制粘贴到计算机上的某个目录下。然后在vs2010的解决方案资源管理器窗口中右击项目,单击“添加引用”,...

    7.Redis学习笔记.pdf

    redis学习笔记,讲解redis的安装使用,基本原理,常见场景,脚本,持久化,事务等高级特性都有讲解

    ServiceStack.Redis-5.8无限制.zip

    ServiceStack.Redis-5.8无限制.zip

    ServiceStack .Redis3.9.60 Redis.NET客户端无限制版

    Redis推荐的最好的.Net客户端。 ServiceStack.Redis 4.0 已经收费 并且有每小时6000次插入的限制。这个是ServiceStack.Redis 3系版本的最终最新版本3.9.60,无使用限制, Redis.NET客户端无限制版

    StackExchange.Redis.dll

    最近需要在C#中使用Redis,ServiceStack.Redis的4.0版本已开始收费,之前版本Bug较多。建议使用StackExchange.Redis,支持异步的客户端,据说性能比ServiceStack.Redis更好,而且据说Stack Overflow也是使用的这个...

    Redis学习笔记整理

    一、 redis 环境搭建 2 二、 redis学习笔记之数据类型 3 三、 redis学习笔记之排序 11 四、 redis学习笔记之事务 16 五、 redis学习笔记之pipeline 20 六、 redis学习笔记之发布订阅...九、 redis学习笔记之虚拟内存 31

    StackExchange.Redis Redis客户端

    最近需要在C#中使用Redis,在Redis的官网找到了ServiceStack.Redis,最后在测试的时候发现这是个坑,4.0已上已经收费,后面只好找到3系列的最终版本,最后测试发现还是有BUG或者是我不会用。没有办法,最好找到了...

    StackExchange.Redis .NET4.0

    StackExchange.Redis .NET4.0,StackExchange.Redis.net4.0的工具类

    ServiceStack.Redis 4.5.0.0破解版去除次数限制

    ServiceStack.Redis 4.5.0.0 已解除license限制

    StackExchange.Redis-1.2.6精简,附64位dll

    C#下非常好用的开源Redis客户端工具,包括内存数据库和pub/sub功能等。 精简工程目录后只包括StackExchange.Redis。代码未做更改。 64位dll在bin目录下。

    Redis学习笔记.pdf

    Redis学习笔记.pdf 含目录 #资源达人分享计划#

    ServiceStack.Redis破除每小时访问6000次的限制

    ServiceStack.Redis版本:5.14.0 使用方法:替换nuget包中ServiceStack.Text.dll即可

    C# StackExchange.Redis 操作封装类库

    C# StackExchange.Redis 操作封装类库,分别封装了Redis五大数据结构(String,Hash,List,Set,ZSet)的增删改查的操作方法,支持Async异步操作。​支持Redis分库操作。支持信息队列操作。 带有单元测试,为每个...

    redis-5.0.5.tar.gz

    redis-5.0.5.redis-5.0.5.redis-5.0.5.redis-5.0.5.redis-5.0.5.redis-5.0.5.redis-5.0.5.redis-5.0.5.redis-5.0.5.redis-5.0.5.redis-5.0.5.redis-5.0.5.redis-5.0.5.redis-5.0.5.redis-5.0.5.redis-5.0.5.redis-...

    Hangfire.Pro.Redis.2.2.2

    Hangfire.Pro.Redis.2.2.2.nupkg,亲测可用,Hangfire.Pro.Redis Background Jobs Throughput Hangfire Pro comes with Hangfire.Pro.Redis package that uses Redis server to persist background jobs and other ...

    封装StackExchange.Redis

    由于ServiceStack.Redis已经收费,所以开始转向StackExchange.Redis使用,这里不讨论性能,只是封装其使用;网上有一位网友的封装我很喜欢,逐步修改了下。把redis几种存储的操作分别封装在一个类中;分别增加了单例...

    TeamDev.Redis.rar

    TeamDev Redis Client , Redis是一个开源的使用ANSI C语言编写、支持网络、可基于内存亦可持久化的日志型、Key-Value数据库,并提供多种语言的API。...TeamDev.Redis.rar客户端dll文件 C#客户端并且有代码示例

    Hangfire.Redis.StackExchange:基于原始(现在不支持)Hangfire.Redis的HangFire Redis存储,但使用可爱的StackExchange.Redis客户端

    Hangfire.Redis.StackExchange 基于Redis的迟发型存储但使用可爱客户端。 包裹名字 NuGet.org Hangfire.Redis.StackExchange Hangfire.Redis.StackExchange.StrongName 强调 支持Hangfire批处理( ) 借助...

Global site tag (gtag.js) - Google Analytics