swoole内核剖析1 -- swArray数组

308 阅读2分钟

swArray数据结构

swArray是swoole的数组结构,实现了空间的预分配。

基本数据结构

typedef struct _swArray
{
    // void *指针数组,页空间
    void **pages;
    // 页的数量
    uint16_t page_num;
    // 页内数据元素的个数
    uint16_t page_size;
    // 数据元素尺寸
    uint32_t item_size;
    // 总的元素个数
    uint32_t item_num;
    // 数组当前的索引位置偏移,用在追加元素中
    uint32_t offset; 
} swArray;

结构图

swArray

基本方法

// 计算索引n位于swArray的哪个页(page)内
#define swArray_page(array, n)      ((n) / (array)->page_size)
// 计算索引n位与swArray指定页内的item的偏移量
#define swArray_offset(array, n)    ((n) % (array)->page_size)

// 新建数组
swArray *swArray_new(int page_size, size_t item_size);
// 销毁数组
void swArray_free(swArray *array);
// 获取数组元素
void *swArray_fetch(swArray *array, uint32_t n);
// 在指定的索引n处存入一个data数据
int swArray_store(swArray *array, uint32_t n, void *data);
// 分配n个元素,如果页不够用,就扩充数组
void *swArray_alloc(swArray *array, uint32_t n);
// 追加一个元素
int swArray_append(swArray *array, void *data);
// 扩展数组,分配一个page页结构
int swArray_extend(swArray *array);
// 清除数组内容
void swArray_clear(swArray *array);

核心技术点分析

  1. 新建一个数组swArray_new,需要定义好每个page中元素的个数和元素的大小;之后使用swArray_extend预分配一个page。

  2. 接着就可以给数组中追加元素了,追加元素swArray_append是基于swArray中的offset属性的,该属性就是当前元素的偏移量,也就是当前元素的索引,是一个累加值。

  3. swArray_store则是在用户指定的索引n上,添加元素

  4. 清除数组

// 单纯的将offset便宜量和item_num元素个数置为0,清除数据,但不释放空间
void swArray_clear(swArray *array)
{
    array->offset = 0;
    array->item_num = 0;
}

// =============== //

// 遍历释放每一个页,并释放pages和整个array内存空间
void swArray_free(swArray *array)
{
    int i;
    // 遍历页的个数
    for (i = 0; i < array->page_num; i++)
    {
        sw_free(array->pages[i]);
    }
    // 释放页变量
    sw_free(array->pages);
    // 释放整个数组
    sw_free(array);
}