zoukankan      html  css  js  c++  java
  • 第二章 简单动态字符串

    在redis中,默认字符串的表示类型是SDS(简单动态字符串),C语言传统的字符串表示只在很少的情况下用到。

    2.1 SDS的定义

      SDS结构:

      char buf[];用于保存字符串,会在字符串结尾自动添加一个空字符,遵循C字符串结尾的惯例,即用N+1字符串数组表示长度为N的字符串

      unsigned int len;buf[]中已使用的长度,不包含自动添加的空字符(原生带有的的空字符需要计算在内),int类型占用内存4byte

      unsigned int free;记录buf[]未使用的字节数量,不包含自动添加的空字符,初始化为0。int类型占用内存为4byte

      

      SDS占用的内存为:4byte + 4byte + n + 1。其中n为存储的字符串长度

    2.2 SDS与C字符串的区别

      2.2.1 获取字符串长度复杂度为O(1)

      因为len属性,可以很快获取字符串长度不需要遍历。

      2.2.2 杜绝缓冲区溢出

      在SDS API对SDS修改时,API 会预先检查是否有足够空间,否则会分配足够的内存,再写入。而C语言中的操作都假设分配的内存是足够的,检查和内存不足的工作都交由上层调用者处理。

      2.2.3 减少修改字符串时带来的内存重分配次数

      C字符串的每次增长或缩短,都需要一次内存重分配:增长需要扩展可使用内存,否则出现缓冲区溢出;缩短需要释放内存,否则出现内存泄漏。内存重分配比较耗时,频繁的内存重分配操作不适用Redis的使用场景。在Redis中通过空间预分配惰性空间释放两种策略优化。

        1. 空间预分配

        扩展时,额外分配 Min(扩展后总大小,1MB) 大小的内存用作缓冲。下次分配时,SDS API 会预先检查缓冲空间,如果够用则直接分配。相对于C字符串的N次扩展都需要N次重分配,SDS将其降低为最多N次重分配。

        2. 惰性空间释放

        缩短时,移除不需要的字节后,并不会立刻缩短分配内存,用free记录当前可使用大小,目的是下次扩展时,需要使用这部分内存。

      2.2.4 二进制安全

      C字符串中间不能带有空字符,否则会被认为是结尾标志。只能用来存储文本。而SDS不依赖这个判断条件,而是根据len属性判断,所以还可以用来二进制数据比如图片、音频视频等。

      2.2.5 兼容部分C字符串函数    

      SDS API依然自动在末尾添加空字符,是为了兼容C字符串函数,避免不必要的代码重复。

          

    人生就像蒲公英,看似自由,其实身不由己。
  • 相关阅读:
    python删除列表重复元素
    maven常用打包命令
    python开发之函数
    手把手教你用Strace诊断问题
    python引用列表--10
    Python中open函数怎么操作文件--9
    python数据操作--8
    图解源码之FutureTask篇(AQS应用)
    图解源码之java锁的获取和释放(AQS)篇
    图解线程池工作机制,手写线程池?
  • 原文地址:https://www.cnblogs.com/walker993/p/14424512.html
Copyright © 2011-2022 走看看