redis虽说是用C语言开发的,但是redis考虑了性能、安全性、效率性、功能等要,redis底层存储字符串实现,自己实现了名为简单动态字符串(Simple dynamic string)简称SDS的结构来存储字符串,这个结构有int len(当前字符串长度), int free(未使用的字符串长度可以说是缓冲), char buf[](存储的字符串数组)这几个变量。

接下来我们开始分析C语言默认字符串和SDS字符串的区别以及redis为什么要使用SDS。

1、C语言的字符串存储并不能记录自身字符串长度,且在内存中实现的方式是|r|e|d|i|s|\0   最后的'\0'表示C语言的结束符,每次调用strlen方法取字符串长度无可避免得去搜索'\0'结束的字符串从而使复杂度变成O(N),redis作为一个高性能的代名词是无法容忍这个缺陷的,所以SDS结构的len变量就有用了直接可以知道这个变量大小是多少,从而使软件的复杂度变成O(1)。

2、C语言的2个字符串在连接得时候容易发生内存溢出问题,比如现在有2个连续的C字符串 a(len=6),b(实际长度8)在内存中分配的地址如下:

|r|e|d|i|s|\b|m|o|n|g|o|d|b|\b|

假如我现在执行strcat(a,"666")操作如果忘记了给a分配新长度的话,内存就会溢出,从而影响b的值,而SDS避免了这个问题,当执行给SDS添加字符串会自动检查当前的free长度是否够用,如果不够会自动分配新空间,从而避免了内存溢出问题,其实说到这里其实SDS作为Redis存储的最细节关键的还是这个free缓冲,因为Redis的使用场景中大部分速度要求苛刻,且经常会发生字符串增加或者减少的事情,而如果每次都调用系统类库来分配内存空间,会很耗时,降低性能,而Redis考虑到了这一点,使用了free,大大减少了内存分配的次数,从而提高了性能。

3、C语言字符串不能用来存储二进制文件,因为c语言字符串利用了'\0'作为字符串结尾,但是二进制文件结尾是-1,而SDS有一个len变量,就解决了这个问题,可以包含多个'\0',从而可以存储任意二进制数据。

4、SDS也遵循了C语言字符串'\0'结尾的规则,使得SDS也可以使用一部分系统的类库。

区别图片

redis数据结构存储SDS设计细节(redis的设计与实现笔记)的更多相关文章

  1. Redis数据结构之sds基本操作函数

    本文及后续文章,Redis版本均是v3.2.8 本篇文章讲解sds基本操作函数,我们从源码角度来进一步理解. 一.sds创建函数和销毁 sds创建函数 /* Create a new sds stri ...

  2. Redis数据结构:SDS

    1. 简单动态字符串(simple dynamic string,SDS)是Redis的默认字符串表示结构,底层的string都是基于SDS实现.Redis基于C语言,并引用了部分C函数. 使用场景: ...

  3. Redis 数据结构 之 SDS

    SDS(simple dynamic string),简单动态字符串.s同时它被称为 Hacking String.hack 的地方就在 sds 保存了字符串的长度以及剩余空间.sds 的实现在 sd ...

  4. redis数据结构存储Dict设计细节(redis的设计与实现笔记)

    说到redis的Dict(字典),虽说算法上跟市面上一般的Dict实现没有什么区别,但是redis的Dict有2个特殊的地方那就是它的rehash(重新散列)和它的字典节点单向链表. 以下是dict用 ...

  5. redis数据结构存储Linked List设计细节(redis的设计与实现笔记)

    redis里拥有一个灵活扩展且获取表头表尾复杂度为O(1)的双端列表,分为list和listNode2部分组成. list: typedef struct list {//链表 listNode *h ...

  6. Redis—数据结构之sds

    Redis是一个Key Value数据库.Redis有5种数据类型:字符串.列表.哈希.集合.有序集合.而字符串的底层实现方法之一就是使用sds.以下描述中请读者注意区分sds是指简单动态字符串这一数 ...

  7. redis数据结构之SDS

    简介 redis源码虽然是C语言实现的,但是Redis没有直接采用C语言传统的字符串表示,而是构建了一种名叫简单动态字符串(simple dynamic string,SDS)的抽象类型,并将SDS用 ...

  8. Redis数据结构和使用场景,redis内存淘汰策略

    什么样的数据适合放入Redis? sql执行耗时特别久,且结果不频繁变动的数据,适合放入Redis. Redis是单线程的,为什么会这么快? 纯内存操作 单线程操作,避免频繁的上下文切换 采用了非阻塞 ...

  9. 为了拿捏 Redis 数据结构,我画了 40 张图(完整版)

    大家好,我是小林. Redis 为什么那么快? 除了它是内存数据库,使得所有的操作都在内存上进行之外,还有一个重要因素,它实现的数据结构,使得我们对数据进行增删查改操作时,Redis 能高效的处理. ...

随机推荐

  1. C++ std::deque

    std::deque template < class T, class Alloc = allocator > class deque; Double ended queue deque ...

  2. Java中六大时间类的使用和区别

    关于java中六个时间类的使用和区别 java.util.Date java.sql.Date  java.sql.Time  java.sql.Timestamp java.text.SimpleD ...

  3. PHP 调用webService方式

    方法如下: <?php header('Content-Type: text/html; charset=UTF-8'); define('APP_ROOT', dirname(__FILE__ ...

  4. Enterprise Solution 企业资源计划管理软件 C/S架构,支持64位系统,企业全面应用集成,制造业信息化

    Enterprise Solution是一套完整的企业资源计划系统,功能符合众多制造业客户要求.系统以.NET Framework技术作为开发架构,完善的功能可有效地帮助企业进行运营策划,减低成本,如 ...

  5. Vue1.0 的技术栈

    vuejs概述 Vue.js是用于构建交互式的Web界面的库.它提供了MVVM数据绑定和一个可组合的组件系统,具有简单.灵活的API. 结合node.js 可以实现前后端开发从物理上的分离.使前端负责 ...

  6. 设计模式(十三):从“FQ”中来认识代理模式(Proxy Pattern)

    我们知道Google早就被墙了,所以FQ才能访问Google呢,这个“FQ”的过程就是一个代理的过程.“代理模式”在之前的博客中不止一次的提及过,之前的委托回调就是代理模式的具体应用.今天我们就从“F ...

  7. 推荐13款javascript模板引擎

    javaScript 在生成各种页面内容时如果能结合一些模板技术,可以让逻辑和数据之间更加清晰,本文介绍 X 款 JavaScript 的模板引擎.(排名不分先后顺序) 1. Mustache 基于j ...

  8. JavaScript学习总结(三)——this、原型、javascript面向对象

    一.this 在JavaScript中this表示:谁调用它,this就是谁. JavaScript是由对象组成的,一切皆为对象,万物皆为对象.this是一个动态的对象,根据调用的对象不同而发生变化, ...

  9. Windows环境下vscode-go安装笔记

    一.介绍 对于Visual Studio Code开发工具,有一款优秀的GoLang插件,它的主页为:https://github.com/microsoft/vscode-go 这款插件的特性包括: ...

  10. 后缀数组(suffix array)详解

    写在前面 在字符串处理当中,后缀树和后缀数组都是非常有力的工具. 其中后缀树大家了解得比较多,关于后缀数组则很少见于国内的资料. 其实后缀数组是后缀树的一个非常精巧的替代品,它比后缀树容易编程实现, ...