You cannot select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.

298 lines
7.5 KiB
C

This file contains ambiguous Unicode characters!

This file contains ambiguous Unicode characters that may be confused with others in your current locale. If your use case is intentional and legitimate, you can safely ignore this warning. Use the Escape button to highlight these characters.

/*****************************************************************************
* file lib/management/array.c
* author YuLiang
* version 1.0.0
* date 22-Sep-2021
* brief This file provides all the array related operation functions.
******************************************************************************
* Attention
*
* <h2><center>&copy; COPYRIGHT(c) 2021 LandPower</center></h2>
*
* Redistribution and use in source and binary forms, with or without modification,
* are permitted provided that the following conditions are met:
* 1. Redistributions of source code must retain the above copyright notice,
* this list of conditions and the following disclaimer.
* 2. Redistributions in binary form must reproduce the above copyright notice,
* this list of conditions and the following disclaimer in the documentation
* and/or other materials provided with the distribution.
* 3. Neither the name of LandPower nor the names of its contributors may be used to
* endorse or promote products derived from this software without specific
* prior written permission.
*
* THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
* AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
* IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
* DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE
* FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
* DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR
* SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER
* CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY,
* OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
* OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
*
******************************************************************************/
/* Includes ------------------------------------------------------------------*/
#ifdef HAVE_CONFIG_H
#include "config.h"
#endif
/* 标准C库头文件. */
/* 用户代码头文件. */
#include "array.h"
/* Private typedef -----------------------------------------------------------*/
/* Private define ------------------------------------------------------------*/
/* Private macro -------------------------------------------------------------*/
/* Private variables ---------------------------------------------------------*/
/* Private function prototypes -----------------------------------------------*/
/* Internal functions --------------------------------------------------------*/
/* 确保设置的数组成员没有内存越界如果超出数组长度则重新realloc:
a -- 数组结构
len -- 需要申请的长度
mem_type -- 使用的内存模块
return: void */
static void _array_len_ensure(array_t *a, uint32_t len, int32_t mem_type)
{
if (a->alloced > len)
{
return;
}
a->index = XREALLOC(mem_type, a->index, sizeof(void *) * (a->alloced * 2));
memset(&a->index[a->alloced], 0, sizeof(void *) * a->alloced);
a->alloced *= 2;
if (a->alloced <= len)
{
_array_len_ensure(a, len, mem_type);
}
}
/* 查找数组a的第一个空位置.
a -- 数组结构
return: 第一个空位置索引 */
uint32_t _array_empty_slot(array_t *a)
{
uint32_t i = 0;
for(i = 0; i < a->active; i++)
{
if (NULL == a->index[i])
{
return i;
}
}
return i;
}
/* Interface functions -------------------------------------------------------*/
/* 初始化数组:
size -- 数组初始大小
mem_type -- 使用的内存模块
return: 数组指针 */
array_t *array_init(uint32_t size, int32_t mem_type)
{
array_t *a = XMALLOC(mem_type, sizeof(array_t));
/* 如果大小为0,设置默认大小. */
if (0 == size)
{
size = ARRAY_MIN_SIZE;
}
a->alloced = size;
a->active = 0;
a->index = XMALLOC(mem_type, sizeof(void *) * size);
return a;
}
/* 设置数组相应索引位置的值:
a -- 数组
i -- 索引
val -- 值
mem_type -- 使用的内存模块
return: void */
void array_set(array_t *a, uint32_t i, void *val, int32_t mem_type)
{
_array_len_ensure(a, i, mem_type);
a->index[i] = val;
if (a->active <= i)
{
a->active = i + 1;
}
}
/* 删除数组相应索引位置的值:
a -- 数组
i -- 索引
return: void */
void array_unset(array_t *a, uint32_t i)
{
if (i >= a->alloced)
{
return;
}
a->index[i] = NULL;
/* 不是最后一个元素直接返回. */
if (i + 1 != a->active)
{
return;
}
/* 如果是最后一个元素,则将当前可使用指针前移. */
while(--a->active)
{
if (a->index[a->active - 1] != NULL)
{
break;
}
}
}
/* 将数据放入数组的第一个空位置:
a -- 数组
val -- 值
mem_type -- 使用的内存模块
return: 数据放入位置的索引值 */
uint32_t array_append(array_t *a, void *val, int32_t mem_type)
{
uint32_t i = 0;
i = _array_empty_slot(a);
_array_len_ensure(a, i, mem_type);
a->index[i] = val;
if (a->active <= i)
{
a->active = i + 1;
}
return i;
}
/* 复制数组a:
a -- 数组
mem_type -- 使用的内存模块
return: 新数组指针 */
array_t *array_copy(array_t *a, int32_t mem_type)
{
unsigned int size = 0;
array_t *array = XMALLOC(mem_type, sizeof(array_t));
array->active = a->active;
array->alloced = a->alloced;
size = sizeof(void *) * (a->alloced);
array->index = XMALLOC(mem_type, size);
memcpy(array->index, a->index, size);
return array;
}
/* 将数组a和数组b合并成数组a:
a -- 数组1
b -- 数组2
mem_type -- 使用的内存模块
return: void */
void array_merge(array_t *a, array_t *b, int32_t mem_type)
{
uint32_t size = 0;
if (0 == b->alloced)
{
return;
}
size = sizeof(void *) * (a->alloced + b->alloced);
a->index = XREALLOC(mem_type, a->index, size);
memcpy(&a->index[a->active], b->index, sizeof(void *) * b->active);
a->active = a->active + b->active;
a->alloced = a->alloced + b->alloced;
}
/* 释放array_t:
a -- 数组
mem_type -- 使用的内存模块
return: void */
void array_free_wrapper(array_t *a, int32_t mem_type)
{
XFREE(mem_type, a);
}
/* 释放array_t->index:
a -- 数组
mem_type -- 使用的内存模块
return: void */
void array_free_index(array_t *a, int32_t mem_type)
{
XFREE(mem_type, a->index);
}
/* 释放array_t和array_t->index:
a -- 数组
mem_type -- 使用的内存模块
return: void */
void array_free(array_t *a, int32_t mem_type)
{
XFREE(mem_type, a->index);
XFREE(mem_type, a);
}
/* 查询数组a的数据i:
a -- 数组
i -- 元素索引
return: 元素指针 */
void *array_lookup(array_t *a, uint32_t i)
{
return (i >= a->active) ? NULL : a->index[i];
}
/* 获取数组a中有效数据的个数:
a -- 数组
return: void */
uint32_t array_count(array_t *a)
{
uint32_t i = 0;
uint32_t count = 0;
for (i = 0; i < a->active; i++)
{
if (a->index[i] != NULL)
{
count++;
}
}
return count;
}
/************************ (C) COPYRIGHT LandPower ***** END OF FILE ****/