文章详情

短信预约-IT技能 免费直播动态提醒

请输入下面的图形验证码

提交验证

短信预约提醒成功

Redis中String字符串和sdshdr结构体超详细讲解

2023-05-15 08:10

关注

前言

在redis中对字符串的处理,个人觉得特别的优雅,所以特意写这篇帖子来分享一下对其的理解。

struct sdshdr {
    int len;
    int free;
    char buf[];
};

len是长度

free是目前空闲的长度

buf是实际存储的字符数组

很多读者,第一次见到char buf[],会感到到,这不是数组么,怎么还能不传入初始大小???

为了用官方的论证这个char buf[],笔者特意找到GCC手册中6.17 Arrays of Length Zero章节,以下截图是对其的描述。

GCC手册的论证

一言以蔽之:就是GCC编译器在ISO C99的C语言规范中支持动态数组。并且初始长度为0。并且只能出现在结构体中最后一个成员。

既然redis定义了自己的字符串形式,那么对字符串的操作那比不可少,所以下面挑选几个api对其讲解。实际上,细心的读者可以发现,其实每个api的操作大同小异,都是通过指针的骚操作得到sdshdr结构体,然后取值。

sdslen讲解

static inline size_t sdslen(const sds s) {
    struct sdshdr *sh = (void*)(s-(sizeof(struct sdshdr)));
    return sh->len;
}

首先需要明白:

sizeof(struct sdshdr) = 8

因为由GCC文档得知可变数组在初始化的过程中大小为0,所以sizeof(struct sdshdr) 仅仅是2个int的大小2*4 = 8;

其次方法参数const sds s是传入的char*地址。也就是sdshdr结构体中char buf[];的地址。

所以使用char buf[];的地址 - 8 就是sdshdr结构体的地址。

文字描述可能存在理解偏差,所以笔者借用图形化来方便读者的理解,如下图所示。

sdsnewlen讲解

// void *init是初始化的字符串
// size_t initlen是长度
sds sdsnewlen(const void *init, size_t initlen) {
    struct sdshdr *sh;
    if (init) {
        // 因为sizeof(struct sdshdr)长度不计算char buf[],
        // 所以开辟大小需要加上initlen,为什么要+1,因为字符串'\0'结尾,所以要+1的大小。
        sh = zmalloc(sizeof(struct sdshdr)+initlen+1);
    } else {
        sh = zcalloc(sizeof(struct sdshdr)+initlen+1);
    }
    if (sh == NULL) return NULL;
    sh->len = initlen;
    sh->free = 0;
    // 把传入的字符串拷贝到sdshdr结构体中的char buf[]中。
    if (initlen && init)
        memcpy(sh->buf, init, initlen);
    // 把字符串的最后一位赋值为'\0'
    sh->buf[initlen] = '\0';
    // 返回char buf[]的地址
    return (char*)sh->buf;
}

仔细的讲解都在代码的注释中。

这里需要注意一点,就是sizeof(struct sdshdr)长度不计算char buf[],所以开辟大小需要加上initlen,为什么要+1,因为字符串'\0'结尾,所以要+1的大小。

其他的api大同小异,就不一一的做讲解了。

总结

到此这篇关于Redis中String字符串和sdshdr结构体超详细讲解的文章就介绍到这了,更多相关Redis String字符串内容请搜索编程网以前的文章或继续浏览下面的相关文章希望大家以后多多支持编程网!

阅读原文内容投诉

免责声明:

① 本站未注明“稿件来源”的信息均来自网络整理。其文字、图片和音视频稿件的所属权归原作者所有。本站收集整理出于非商业性的教育和科研之目的,并不意味着本站赞同其观点或证实其内容的真实性。仅作为临时的测试数据,供内部测试之用。本站并未授权任何人以任何方式主动获取本站任何信息。

② 本站未注明“稿件来源”的临时测试数据将在测试完成后最终做删除处理。有问题或投稿请发送至: 邮箱/279061341@qq.com QQ/279061341

软考中级精品资料免费领

  • 历年真题答案解析
  • 备考技巧名师总结
  • 高频考点精准押题
  • 2024年上半年信息系统项目管理师第二批次真题及答案解析(完整版)

    难度     801人已做
    查看
  • 【考后总结】2024年5月26日信息系统项目管理师第2批次考情分析

    难度     348人已做
    查看
  • 【考后总结】2024年5月25日信息系统项目管理师第1批次考情分析

    难度     311人已做
    查看
  • 2024年上半年软考高项第一、二批次真题考点汇总(完整版)

    难度     432人已做
    查看
  • 2024年上半年系统架构设计师考试综合知识真题

    难度     220人已做
    查看

相关文章

发现更多好内容

猜你喜欢

AI推送时光机
位置:首页-资讯-后端开发
咦!没有更多了?去看看其它编程学习网 内容吧
首页课程
资料下载
问答资讯