整数集合(intset)是Redis用来保存整数值当集合抽象数据结构,可以保存类型位
int16_t
、
int32_t
、
int64_t
都整数值,且不会出现重复元素
整数集合用intset.h
文件内的intset
结构表示
typedef struct intset {
// 编码方式
uint32_t encoding;
// 集合包含的元素数量
uint32_t length;
// 保存元素的数组
int8_t contents[];
} intset;
contents
数组是底层实现,整数集合的每个元素都是其中的一个数组项,且按照从小到大排序,并且不包含任何重复项
contents
并不保存任何int8_t
类型的值,它的真正类型取决于encoding
的值
- 如果值为INTSET_ENC_INT16,那么
contents
的类型为int16_t
- INTSET_ENC_INT32 …
- INTSET_ENC_INT64 …
升级规则 :当一个底层为较小类型数组(例如int16_t
)的整数集合保存了一个较大类型的元素(例如int64_t
),那么整数集合已有的所有元素都会转换成较大类型的元素(例如int16_t
升级为int64_t
)
升级
每当添加一个新的元素,且新元素的类型比整数集合现有的所有元素的类型都要长时,整数集合需要先升级,然后才能添加新元素到集合里
升级并添加新元素分3步进行:
- 根据新元素类型,扩展整数集合底层数组的空间大小,并为新元素分配空间
- 将所有元素转换成与新元素相同的类型,且把转换后的元素放到正确的位上。放置的过程中,底层数组的有序性不变
- 添加新元素
引发升级的新元素的长度总是比其他元素都要大,因此它的值要么比其他元素都要大,要么就比其他元素都要小
- 比其他元素都小,则放到数组的开头
- 比其他元素都大,则放到数组的末尾
升级的好处
提升灵活性
C语言是静态类型语言,因此同一个数据结构一般只存放一种数据类型的值
自动升级使得整数集合可以自适应地添加元素,不必担心出现类型错误
节约内存
升级操作只在有需要的时候进行,因此不必为了兼容所有类型而在一开始设定一个较大类型的数组,这样可以尽量节约内存
降级
整数集合不支持降级