本文分析Redis字符串的实现原理,内容摘自新书《Redis核心原理与实践》。这本书深入地分析了Redis常用特性的内部机制与实现方式,内容源自对Redis源码的分析,并从中总结出设计思路、实现原理。通过阅读本书,读者可以快速、轻松地了解Redis的内部运行机制。
Redis是一个键值对数据库(key-value DB),下面是一个简单的Redis的命令:

本书第1部分会对表1-1中前五种数据类型进行分析,最后两种数据类型会在第5部分进行分析。如果读者现在对表1-1中内容感到疑惑,则可以先带着疑问继续阅读本书。
我们知道,C语言中将空字符结尾的字符数组作为字符串,而Redis对此做了扩展,定义了字符串类型sds(Simple Dynamic String)。
Redis键都是字符串类型,Redis中最简单的值类型也是字符串类型,
字符串类型的Redis值可用于很多场景,如缓存HTML片段、记录用户登录信息等。
提示:本节代码如无特殊说明,均在sds.h/sds.c中。
对于不同长度的字符串,Redis定义了不同的sds结构体:

sds的扩容机制是一个很重要的功能。

从图1-2中可以看到,使用len记录字符串长度后,字符串中可以存放空字符。Redis字符串支持二进制安全,可以将用户的输入存储为没有任何特定格式意义的原始数据流,因此Redis字符串可以存储任何数据,比如图片数据流或序列化对象。C语言字符串将空字符作为字符串结尾的特定标记字符,它不是二进制安全的。
sds常用函数如表1-2所示。
| 函数 | 作用 |
|---|---|
| sdsnew,sdsempty | 创建sds |
| sdsfree,sdsclear,sdsRemoveFreeSpace | 释放sds,清空sds中的字符串内容,移除sds剩余的可用空间 |
| sdslen | 获取sds字符串长度 |
| sdsdup | 将给定字符串复制到sds中,覆盖原字符串 |
| sdscat | 将给定字符串拼接到sds字符串内容后 |
| sdscmp | 对比两个sds字符串是否相同 |
| sdsrange | 获取子字符串,不在指定范围内的字符串将被清除 |
字符串类型一共有3种编码:
在该编码中,redisObject、sds结构存放在一块连续内存块中,如图1-3所示。

OBJ_ENCODING_EMBSTR编码是Redis针对短字符串的优化,有如下优点:
(1)内存申请和释放都只需要调用一次内存操作函数。
(2)redisObject、sdshdr结构保存在一块连续的内存中,减少了内存碎片。
我们向Redis发送一个请求后,Redis会解析请求报文,并将命令、参数转化为redisObjec。
object.c/createStringObject函数负责完成该操作:

Redis中的键都是字符串类型,并使用OBJ_ENCODING_RAW、OBJ_ENCODING_ EMBSTR编码,而Redis还会尝试将字符串类型的值转换为OBJ_ENCODING_INT 编码。object.c/tryObjectEncoding函数完成该操作:
京东链接到此这篇关于Redis核心原理与实践之字符串实现原理的文章就介绍到这了,更多相关Redis字符串实现原理内容请搜索以前的文章或继续浏览下面的相关文章希望大家以后多多支持!