摘自zabbix,STL模板,很经典
/*
* vectorimpl.h
*
* Created on: 2017年1月22日
* Author: yangling
*/
#ifndef VECTORIMPL_H_
#define VECTORIMPL_H_
#define VECTOR_ARRAY_GROWTH_FACTOR 3/2
#define VECTOR_IMPL(__id, __type) \
\
void __vector_ ## __id ## _ensure_free_space(vector_ ## __id ## _t *vector)\
{ \
if (NULL == vector->values) \
{ \
vector->values_num = 0; \
vector->values_alloc = 32; \
vector->values = (__type *)vector->mem_malloc_func(NULL, vector->values_alloc * sizeof(__type)); \
} \
else if (vector->values_num == vector->values_alloc) \
{ \
vector->values_alloc = MAX(vector->values_alloc + 1, vector->values_alloc * VECTOR_ARRAY_GROWTH_FACTOR); \
vector->values = (__type *)vector->mem_realloc_func(vector->values, vector->values_alloc * sizeof(__type)); \
} \
} \
\
void vector_ ## __id ## _create(vector_ ## __id ## _t *vector) \
{ \
vector_ ## __id ## _create_ext(vector, \
DEFAULT_MEM_MALLOC_FUNC, \
DEFAULT_MEM_REALLOC_FUNC, \
DEFAULT_MEM_FREE_FUNC); \
} \
\
void vector_ ## __id ## _create_ext(vector_ ## __id ## _t *vector, \
mem_malloc_func_t mem_malloc_func, \
mem_realloc_func_t mem_realloc_func, \
mem_free_func_t mem_free_func) \
{ \
vector->values = NULL; \
vector->values_num = 0; \
vector->values_alloc = 0; \
\
vector->mem_malloc_func = mem_malloc_func; \
vector->mem_realloc_func = mem_realloc_func; \
vector->mem_free_func = mem_free_func; \
} \
\
void vector_ ## __id ## _destroy(vector_ ## __id ## _t *vector) \
{ \
if (NULL != vector->values) \
{ \
vector->mem_free_func(vector->values); \
vector->values = NULL; \
vector->values_num = 0; \
vector->values_alloc = 0; \
} \
\
vector->mem_malloc_func = NULL; \
vector->mem_realloc_func = NULL; \
vector->mem_free_func = NULL; \
} \
\
void vector_ ## __id ## _append(vector_ ## __id ## _t *vector, __type value) \
{ \
__vector_ ## __id ## _ensure_free_space(vector); \
vector->values[vector->values_num++] = value; \
} \
\
void vector_ ## __id ## _append_ptr(vector_ ## __id ## _t *vector, __type *value) \
{ \
__vector_ ## __id ## _ensure_free_space(vector); \
vector->values[vector->values_num++] = *value; \
} \
\
void vector_ ## __id ## _append_vector(vector_ ## __id ## _t *vector, vector_ ## __id ## _t *src)\
{ \
vector_ ## __id ## _reserve(vector, vector->values_num + src->values_num); \
memcpy(vector->values + vector->values_num, src->values, src->values_num * sizeof(__type)); \
vector->values_num = vector->values_num + src->values_num; \
} \
\
void vector_ ## __id ## _remove_noorder(vector_ ## __id ## _t *vector, int index) \
{ \
if (!(0 <= index && index < vector->values_num)) \
{ \
my_log_crit( "removing a non-existent element at index %d", index); \
exit(EXIT_FAILURE); \
} \
\
vector->values[index] = vector->values[--vector->values_num]; \
} \
\
void vector_ ## __id ## _remove(vector_ ## __id ## _t *vector, int index) \
{ \
if (!(0 <= index && index < vector->values_num)) \
{ \
my_log_crit( "removing a non-existent element at index %d", index); \
exit(EXIT_FAILURE); \
} \
\
vector->values_num--; \
memmove(&vector->values[index], &vector->values[index + 1], \
sizeof(__type) * (vector->values_num - index)); \
} \
\
void vector_ ## __id ## _sort(vector_ ## __id ## _t *vector, compare_func_t compare_func) \
{ \
if (2 <= vector->values_num) \
qsort(vector->values, vector->values_num, sizeof(__type), compare_func); \
} \
\
void vector_ ## __id ## _uniq(vector_ ## __id ## _t *vector, compare_func_t compare_func) \
{ \
if (2 <= vector->values_num) \
{ \
int i, j = 1; \
\
for (i = 1; i < vector->values_num; i++) \
{ \
if (0 != compare_func(&vector->values[i - 1], &vector->values[i])) \
vector->values[j++] = vector->values[i]; \
} \
\
vector->values_num = j; \
} \
} \
\
int vector_ ## __id ## _nearestindex(const vector_ ## __id ## _t *vector, const __type value, \
compare_func_t compare_func) \
{ \
int lo = 0, hi = vector->values_num, mid, c; \
\
while (1 <= hi - lo) \
{ \
mid = (lo + hi) / 2; \
\
c = compare_func(&vector->values[mid], &value); \
\
if (0 > c) \
{ \
lo = mid + 1; \
} \
else if (0 == c) \
{ \
return mid; \
} \
else \
hi = mid; \
} \
\
return hi; \
} \
\
int vector_ ## __id ## _bsearch(const vector_ ## __id ## _t *vector, const __type value, \
compare_func_t compare_func) \
{ \
__type *ptr; \
\
ptr = (__type *)ext_bsearch(&value, vector->values, vector->values_num, sizeof(__type), compare_func); \
\
if (NULL != ptr) \
return (int)(ptr - vector->values); \
else \
return FAIL; \
} \
\
int vector_ ## __id ## _lsearch(const vector_ ## __id ## _t *vector, const __type value, int *index,\
compare_func_t compare_func) \
{ \
while (*index < vector->values_num) \
{ \
int c = compare_func(&vector->values[*index], &value); \
\
if (0 > c) \
{ \
(*index)++; \
continue; \
} \
\
if (0 == c) \
return SUCCEED; \
\
if (0 < c) \
break; \
} \
\
return FAIL; \
} \
\
int vector_ ## __id ## _search(const vector_ ## __id ## _t *vector, const __type value, \
compare_func_t compare_func) \
{ \
int index; \
\
for (index = 0; index < vector->values_num; index++) \
{ \
if (0 == compare_func(&vector->values[index], &value)) \
return index; \
} \
\
return FAIL; \
} \
\
\
void vector_ ## __id ## _setdiff(vector_ ## __id ## _t *left, const vector_ ## __id ## _t *right,\
compare_func_t compare_func) \
{ \
int c, block_start, deleted = 0, left_index = 0, right_index = 0; \
\
while (left_index < left->values_num && right_index < right->values_num) \
{ \
c = compare_func(&left->values[left_index], &right->values[right_index]); \
\
if (0 >= c) \
left_index++; \
\
if (0 <= c) \
right_index++; \
\
if (0 != c) \
continue; \
\
if (0 < deleted++) \
{ \
memmove(&left->values[block_start - deleted + 1], &left->values[block_start], \
(left_index - 1 - block_start) * sizeof(__type)); \
} \
\
block_start = left_index; \
} \
\
if (0 < deleted) \
{ \
memmove(&left->values[block_start - deleted], &left->values[block_start], \
(left->values_num - block_start) * sizeof(__type)); \
left->values_num -= deleted; \
} \
} \
\
void vector_ ## __id ## _reserve(vector_ ## __id ## _t *vector, size_t size) \
{ \
if ((int)size > vector->values_alloc) \
{ \
vector->values_alloc = (int)size; \
vector->values =(__type *)vector->mem_realloc_func(vector->values, vector->values_alloc * sizeof(__type)); \
} \
} \
\
void vector_ ## __id ## _clear(vector_ ## __id ## _t *vector) \
{ \
vector->values_num = 0; \
} \
#define PTR_VECTOR_IMPL(__id, __type) \
\
VECTOR_IMPL(__id, __type); \
\
void vector_ ## __id ## _clear_ext(vector_ ## __id ## _t *vector, clean_func_t clean_func) \
{ \
if (0 != vector->values_num) \
{ \
int index; \
\
for (index = 0; index < vector->values_num; index++) \
clean_func(vector->values[index]); \
\
vector->values_num = 0; \
} \
}
#endif /* VECTORIMPL_H_ */
用法:
VECTOR_IMPL(uint64, uint64_t);
//VECTOR_IMPL(ptr_pair, ptr_pair_t);
//VECTOR_IMPL(uint64_pair, uint64_pair_t);
PTR_VECTOR_IMPL(str, char *);