zoukankan      html  css  js  c++  java
  • Redis设计与实现(一)简单动态字符串

    Redis没有使用C中自带的String,而是自己构建了一个字符串类,名为Simple Dynamic String。缩写为SDS,下文的SDS就是指此玩意。SDS是redis中默认的字符串使用。而Redis是基于C实现的,C内部的自带的String被它作用于log的记录。也就是一个简单的字符串字面量。当Redis在数据库中新建一个对象的时候(set  msg "nb"),KV中的Key是一个SDS,而Value则是Redis自身实现的SDS对象。当redis中使用RPUSH msg "1" "2"这种情况下 key依然是一个SDS,但是value则为一个列表对象,列表里面存储着2个SDS。

    除了用来保存里面的字符串值对象,SDS也会被用来做缓存区,例如AOF中的缓存区,客户端状态中的输入缓冲区。

    那么SDS是什么呢?我们写代码的人应该能感知出来,这个玩意应该就是对基础数据的封装,然后加入了自己需要的特性。

    源码中SDS是一个对象,里面有三个成员变量,int len用来记录已经使用的长度。也就是字符串的长度,int free表示数组中还剩余的空间。char [] buf表示容器用来存储字符串。

     还是很好理解的吧,SDS遵守了C中以空字符结尾的特点,所以最后一位并没有被算入长度中。所以输出的时候完成可以使用c中自带的print来进行。printf("%s",s->buf)。

    自己使用SDS的好处也很明显,就是利用了哨兵的思想,这样的话知道一个字符串的长度的时间复杂度就可以从O(N)直接变成O(1)。

    另外一个好处就是,不会造成缓存的溢出,这一点Java程序员可能感受不到,理解就是一个操作在执行的时候,因为C是用空字符里进行切割的,例如5+5的字符串组合,如何5变成了6的长度,那么就会溢出到下一个字符串,造成了污染。而SDS存储了长度,就会在每一次修改的时候,进行时候的check。保证这种情况不会出现。

    最后一个特点就是使用SDS可以防止空间的重复操作,什么意思,就是字符串变大变小都需要在C里面对空间进行释放。而SDS这种情况就可以通过"空间预分配",通俗点就是每次多给一点空间,"惰性空间分配",在给字符串锁缩短的时候也会保留多出的空间。这样的话就不需要进行重复的数组重分配了。

    SDS同时可以保存C中字符串无法保存的一些数据,因为C中的字符串是不可以有空的,不然会被认为是结尾,这样的话很多的图片什么的都无法进行保存了,但是SDS是通过长度来进行判断的,所有可以保证的一点就是你存入的数据我都会完整的给你。

    至于为什么SDS也是空结尾,这是为了也可以对C中的String做到一点的重用,也可以使用C中的部分函数。

    smartcat.994
  • 相关阅读:
    常见的分布式协议与算法【转】
    Linux的文件系统及文件缓存知识点整理【转】
    linux内核启动内核解压过程分析【转】
    Linux内核分析:Linux内核启动流程分析【转】
    Linux内核Ramdisk(initrd)机制【转】
    基于tiny4412的Linux内核移植 -- 设备树的展开【转】
    linux中RamDisk的三种实现方式【转】
    (十四)Linux kernel mmc 框架说明,包括mmc_test使用方法【转】
    ApplicationContext的初始化与销毁&Bean的生命周期&BeanPostProcessor的使用&Aware使用(四)
    Spring技术与内幕IoC实现(二)
  • 原文地址:https://www.cnblogs.com/SmartCat994/p/14139015.html
Copyright © 2011-2022 走看看