欢迎您访问 最编程 本站为您分享编程语言代码,编程技术文章!
您现在的位置是: 首页

Redis 源代码学习日志:string-sdsrange

最编程 2024-04-30 18:14:01
...

sds 中存储的字符串修改为,[start, end] 这个子串。

void sdsrange(sds s, int start, int end) {
    size_t newlen, len = sdslen(s); // len: s 中存储数据的字节数

    if (len == 0) return; // 如果源 sds 中没有存储数据结束函数调用
    // 下面的很长一段代码都是对 start 和 end 的修正哈
    if (start < 0) { // 根据这个 start 和 end 的判断来看,是支持负的 start 和 end 呢!类似于负的下标吧
        start = len+start; 
        if (start < 0) start = 0;
    }
    if (end < 0) {
        end = len+end;
        if (end < 0) end = 0;
    }
    // 子串的长度,要求 start <= end
    newlen = (start > end) ? 0 : (end-start)+1;
    // 修正 newlen
    if (newlen != 0) {
        if (start >= (signed)len) { 
            newlen = 0;
        } else if (end >= (signed)len) {
            end = len-1;
            newlen = (start > end) ? 0 : (end-start)+1;
        }
    } else {
        start = 0;
    }
    // 只有当 start != 0 并且 newlen != 0 的时候才需要挪动数据
    // 可以使用 memcpy 吗?这个问题不好说哈,因为在发现 memcpy 的问题之后,memcpy 的底层实现应该就是修改成了 memmove 了吧!
    if (start && newlen) memmove(s, s+start, newlen);
    s[newlen] = 0; // 在字符串的末尾提那集 '\0'
    // 修改 sds 的 len 属性
    sdssetlen(s,newlen);
}