Compare commits
20 Commits
| Author | SHA1 | Date | |
|---|---|---|---|
| b57d8a95a9 | |||
| 6dc339f0f2 | |||
| af716348a6 | |||
| eefe5e2c8f | |||
| c0294bc1f0 | |||
| f90afd3df8 | |||
| 828fe1caac | |||
| 98cee61c83 | |||
| d079bb1a61 | |||
| 7b4f6b2671 | |||
| 932849a062 | |||
| 7d84d2968a | |||
| 38bef70bc5 | |||
| 4dfe971282 | |||
| bdebf87267 | |||
| 90341ae51c | |||
| 0881ba9076 | |||
| 834ab672bc | |||
| 2ee1d73def | |||
| 76ca84f72e |
@@ -12,6 +12,11 @@ typedef struct libcdsb_stack_node {
|
|||||||
void* value;
|
void* value;
|
||||||
} stack_t;
|
} stack_t;
|
||||||
|
|
||||||
|
typedef struct libcdsb_queue {
|
||||||
|
struct libcdsb_stack_node* back;
|
||||||
|
struct libcdsb_stack_node* front;
|
||||||
|
} queue_t;
|
||||||
|
|
||||||
extern void libcdsb_stack_init (stack_t* stack) Nonnull__(1);
|
extern void libcdsb_stack_init (stack_t* stack) Nonnull__(1);
|
||||||
extern void libcdsb_stack_push (stack_t* stack, void* value) Nonnull__(1);
|
extern void libcdsb_stack_push (stack_t* stack, void* value) Nonnull__(1);
|
||||||
extern void libcdsb_stack_push_many(stack_t* stack, size_t n, ...) Nonnull__(1);
|
extern void libcdsb_stack_push_many(stack_t* stack, size_t n, ...) Nonnull__(1);
|
||||||
@@ -19,6 +24,12 @@ extern void* libcdsb_stack_pop (stack_t* stack) Nonnull__(1)
|
|||||||
extern void libcdsb_stack_reverse (stack_t* stack) Nonnull__(1);
|
extern void libcdsb_stack_reverse (stack_t* stack) Nonnull__(1);
|
||||||
extern void libcdsb_stack_flush (stack_t* stack) Nonnull__(1);
|
extern void libcdsb_stack_flush (stack_t* stack) Nonnull__(1);
|
||||||
|
|
||||||
|
extern void libcdsb_queue_init (queue_t* queue) Nonnull__(1);
|
||||||
|
extern void libcdsb_queue_push (queue_t* queue, void* value) Nonnull__(1);
|
||||||
|
extern void libcdsb_queue_push_many(queue_t* queue, size_t n, ...) Nonnull__(1);
|
||||||
|
extern void* libcdsb_queue_pop (queue_t* queue) Nonnull__(1);
|
||||||
|
extern void libcdsb_queue_flush (queue_t* queue) Nonnull__(1);
|
||||||
|
|
||||||
extern void* libcdsb_aalloc (size_t a, size_t n) Warn_unused_result__;
|
extern void* libcdsb_aalloc (size_t a, size_t n) Warn_unused_result__;
|
||||||
extern void* libcdsb_malloc (size_t n) Warn_unused_result__;
|
extern void* libcdsb_malloc (size_t n) Warn_unused_result__;
|
||||||
extern void* libcdsb_calloc (size_t n, size_t c) Warn_unused_result__;
|
extern void* libcdsb_calloc (size_t n, size_t c) Warn_unused_result__;
|
||||||
|
|||||||
+7
-11
@@ -19,10 +19,8 @@ inline void dict_init(vtype_dict* x) { x->nodes = (void*)(x->capacity = x->size
|
|||||||
|
|
||||||
#define dict_pop(x, key, data, callback) libcdsb_dict_find (x, _LIBCDSB_value_pointer(key), _LIBCDSB_vtypeof(key), data, callback, 1)
|
#define dict_pop(x, key, data, callback) libcdsb_dict_find (x, _LIBCDSB_value_pointer(key), _LIBCDSB_vtypeof(key), data, callback, 1)
|
||||||
#define dict_get(x, key, data, callback) libcdsb_dict_find (x, _LIBCDSB_value_pointer(key), _LIBCDSB_vtypeof(key), data, callback, 0)
|
#define dict_get(x, key, data, callback) libcdsb_dict_find (x, _LIBCDSB_value_pointer(key), _LIBCDSB_vtypeof(key), data, callback, 0)
|
||||||
#define dict_update(x, key, value) libcdsb_dict_update (x, _LIBCDSB_value_pointer(key), _LIBCDSB_vtypeof(key), _LIBCDSB_value_pointer(value), _LIBCDSB_vtypeof(value))
|
#define dict_update(x, key, value) libcdsb_dict_update (x, _LIBCDSB_value_pointer(key), _LIBCDSB_vtypeof(key), _LIBCDSB_value_pointer(value), _LIBCDSB_vtypeof(value), 0, 0)
|
||||||
#define dict_inject(x, key, value) libcdsb_dict_inject (x, _LIBCDSB_value_pointer(key), _LIBCDSB_vtypeof(key), _LIBCDSB_value_pointer(value), _LIBCDSB_vtypeof(value))
|
#define dict_inject(x, key, value) libcdsb_dict_inject (x, _LIBCDSB_value_pointer(key), _LIBCDSB_vtypeof(key), _LIBCDSB_value_pointer(value), _LIBCDSB_vtypeof(value), 0, 0)
|
||||||
#define dict_inject_key(x, key, value) libcdsb_dict_inject_key (x, _LIBCDSB_value_pointer(key), _LIBCDSB_vtypeof(key), _LIBCDSB_value_pointer(value), _LIBCDSB_vtypeof(value))
|
|
||||||
#define dict_inject_value(x, key, value) libcdsb_dict_inject_value(x, _LIBCDSB_value_pointer(key), _LIBCDSB_vtypeof(key), _LIBCDSB_value_pointer(value), _LIBCDSB_vtypeof(value))
|
|
||||||
#define dict_foreach(x, data, callback) libcdsb_dict_foreach (x, data, callback, 0)
|
#define dict_foreach(x, data, callback) libcdsb_dict_foreach (x, data, callback, 0)
|
||||||
#define dict_remove(x, key) dict_pop (x, key, 0, 0)
|
#define dict_remove(x, key) dict_pop (x, key, 0, 0)
|
||||||
|
|
||||||
@@ -30,12 +28,10 @@ inline void dict_init(vtype_dict* x) { x->nodes = (void*)(x->capacity = x->size
|
|||||||
|
|
||||||
/*#####################################################################################################################*/
|
/*#####################################################################################################################*/
|
||||||
|
|
||||||
extern bool libcdsb_dict_update (vtype_dict* x, const void* key, vtype key_type, const void* value, vtype value_type) Nonnull__(1);
|
extern bool libcdsb_dict_update (vtype_dict* x, const void* key, vtype key_type, const void* value, vtype value_type, void* data, dict_access_callback) Nonnull__(1);
|
||||||
extern bool libcdsb_dict_inject (vtype_dict* x, const void* key, vtype key_type, const void* value, vtype value_type) Nonnull__(1);
|
extern bool libcdsb_dict_inject (vtype_dict* x, const void* key, vtype key_type, const void* value, vtype value_type, void* data, dict_access_callback) Nonnull__(1);
|
||||||
extern bool libcdsb_dict_inject_key (vtype_dict* x, const void* key, vtype key_type, const void* value, vtype value_type) Nonnull__(1);
|
extern int libcdsb_dict_find (vtype_dict* x, const void* key, vtype key_type, void* data, dict_access_callback, bool cut) Nonnull__(1);
|
||||||
extern bool libcdsb_dict_inject_value (vtype_dict* x, const void* key, vtype key_type, const void* value, vtype value_type) Nonnull__(1);
|
extern int libcdsb_dict_foreach (vtype_dict* x, void* data, dict_access_callback, bool flush) Nonnull__(1,3);
|
||||||
extern int libcdsb_dict_find (vtype_dict* x, const void* key, vtype key_type, void* data, dict_access_callback, bool cut) Nonnull__(1);
|
extern bool libcdsb_dict_shrink_to_fit(vtype_dict* x) Nonnull__(1);
|
||||||
extern int libcdsb_dict_foreach (vtype_dict* x, void* data, dict_access_callback, bool flush) Nonnull__(1,3);
|
|
||||||
extern bool libcdsb_dict_shrink_to_fit(vtype_dict* x) Nonnull__(1);
|
|
||||||
|
|
||||||
#endif /* LIBCDSB_DICT_H */
|
#endif /* LIBCDSB_DICT_H */
|
||||||
|
|||||||
+12
-12
@@ -28,12 +28,12 @@ inline void list_init (vtype_list* x) { x->first = x->last = 0; }
|
|||||||
#define list_find(x, value, data, callback) libcdsb_list_find (x, _LIBCDSB_value_pointer(value), _LIBCDSB_vtypeof(value), data, callback, 0, 0)
|
#define list_find(x, value, data, callback) libcdsb_list_find (x, _LIBCDSB_value_pointer(value), _LIBCDSB_vtypeof(value), data, callback, 0, 0)
|
||||||
#define list_rfind(x, value, data, callback) libcdsb_list_find (x, _LIBCDSB_value_pointer(value), _LIBCDSB_vtypeof(value), data, callback, 1, 0)
|
#define list_rfind(x, value, data, callback) libcdsb_list_find (x, _LIBCDSB_value_pointer(value), _LIBCDSB_vtypeof(value), data, callback, 1, 0)
|
||||||
#define list_countof(x, value) libcdsb_list_count (x, _LIBCDSB_value_pointer(value), _LIBCDSB_vtypeof(value))
|
#define list_countof(x, value) libcdsb_list_count (x, _LIBCDSB_value_pointer(value), _LIBCDSB_vtypeof(value))
|
||||||
#define list_insert(x, index, value) libcdsb_list_insert (x, index, _LIBCDSB_value_pointer(value), _LIBCDSB_vtypeof(value), -1)
|
#define list_insert(x, index, value) libcdsb_list_insert (x, index, _LIBCDSB_value_pointer(value), _LIBCDSB_vtypeof(value), -1, 0, 0)
|
||||||
#define list_replace(x, index, value) libcdsb_list_insert (x, index, _LIBCDSB_value_pointer(value), _LIBCDSB_vtypeof(value), 0)
|
#define list_replace(x, index, value) libcdsb_list_insert (x, index, _LIBCDSB_value_pointer(value), _LIBCDSB_vtypeof(value), 0, 0, 0)
|
||||||
#define list_push_back(x, value) libcdsb_list_insert (x, -1, _LIBCDSB_value_pointer(value), _LIBCDSB_vtypeof(value), 1)
|
#define list_push_back(x, value) libcdsb_list_insert (x, -1, _LIBCDSB_value_pointer(value), _LIBCDSB_vtypeof(value), 1, 0, 0)
|
||||||
#define list_push_front(x, value) libcdsb_list_insert (x, 0, _LIBCDSB_value_pointer(value), _LIBCDSB_vtypeof(value), -1)
|
#define list_push_front(x, value) libcdsb_list_insert (x, 0, _LIBCDSB_value_pointer(value), _LIBCDSB_vtypeof(value), -1, 0, 0)
|
||||||
#define list_attach_back(x, value) libcdsb_list_attach (x, -1, _LIBCDSB_value_pointer(value), _LIBCDSB_vtypeof(value), 1)
|
#define list_attach_back(x, value) libcdsb_list_attach (x, -1, _LIBCDSB_value_pointer(value), _LIBCDSB_vtypeof(value), 1, 0, 0)
|
||||||
#define list_attach_front(x, value) libcdsb_list_attach (x, 0, _LIBCDSB_value_pointer(value), _LIBCDSB_vtypeof(value), -1)
|
#define list_attach_front(x, value) libcdsb_list_attach (x, 0, _LIBCDSB_value_pointer(value), _LIBCDSB_vtypeof(value), -1, 0, 0)
|
||||||
#define list_foreach(x, data, callback) libcdsb_list_foreach(x, data, callback, 0)
|
#define list_foreach(x, data, callback) libcdsb_list_foreach(x, data, callback, 0)
|
||||||
#define list_remove(x, value) list_pop (x, value, 0, 0)
|
#define list_remove(x, value) list_pop (x, value, 0, 0)
|
||||||
#define list_remove_by_index(x, index) list_pop_by_index (x, index, 0, 0)
|
#define list_remove_by_index(x, index) list_pop_by_index (x, index, 0, 0)
|
||||||
@@ -42,12 +42,12 @@ inline void list_init (vtype_list* x) { x->first = x->last = 0; }
|
|||||||
|
|
||||||
/*#####################################################################################################################*/
|
/*#####################################################################################################################*/
|
||||||
|
|
||||||
extern bool libcdsb_list_insert (vtype_list* x, ssize_t index, const void* value, vtype type, int ins_direction) Nonnull__(1);
|
extern bool libcdsb_list_insert (vtype_list* x, ssize_t index, const void* value, vtype type, int ins_direction, void* data, list_access_callback) Nonnull__(1);
|
||||||
extern bool libcdsb_list_attach (vtype_list* x, ssize_t index, const void* value, vtype type, int ins_direction) Nonnull__(1);
|
extern bool libcdsb_list_attach (vtype_list* x, ssize_t index, const void* value, vtype type, int ins_direction, void* data, list_access_callback) Nonnull__(1);
|
||||||
extern int libcdsb_list_find (vtype_list* x, const void* value, vtype type, void* data, list_access_callback, bool reverse, bool cut) Nonnull__(1);
|
extern int libcdsb_list_find (vtype_list* x, const void* value, vtype type, void* data, list_access_callback, bool reverse, bool cut) Nonnull__(1);
|
||||||
extern int libcdsb_list_get (vtype_list* x, ssize_t index, void* data, list_access_callback, bool cut) Nonnull__(1);
|
extern int libcdsb_list_get (vtype_list* x, ssize_t index, void* data, list_access_callback, bool cut) Nonnull__(1);
|
||||||
extern int libcdsb_list_foreach (vtype_list* x, void* data, list_access_callback, bool flush) Nonnull__(1,3);
|
extern int libcdsb_list_foreach (vtype_list* x, void* data, list_access_callback, bool flush) Nonnull__(1,3);
|
||||||
|
|
||||||
extern size_t libcdsb_list_count(const vtype_list* s, const void* value, vtype type) Pure__ Warn_unused_result__ Nonnull__(1);
|
extern size_t libcdsb_list_count(const vtype_list* s, const void* value, vtype type) Pure__ Warn_unused_result__ Nonnull__(1);
|
||||||
|
|
||||||
#endif /* LIBCDSB_LIST_H */
|
#endif /* LIBCDSB_LIST_H */
|
||||||
|
|||||||
+10
-10
@@ -16,20 +16,20 @@ extern void map_init(vtype_map* x, vtype key_type) Nonnull__(1);
|
|||||||
|
|
||||||
/*#####################################################################################################################*/
|
/*#####################################################################################################################*/
|
||||||
|
|
||||||
#define map_pop(x, key, data, callback) libcdsb_map_find (x, _LIBCDSB_value_pointer(key), _LIBCDSB_vtypeof(key), data, callback, 1)
|
#define map_pop(x, key, data, callback) libcdsb_map_find (x, _LIBCDSB_value_pointer(key), _LIBCDSB_vtypeof(key), data, callback, 1)
|
||||||
#define map_get(x, key, data, callback) libcdsb_map_find (x, _LIBCDSB_value_pointer(key), _LIBCDSB_vtypeof(key), data, callback, 0)
|
#define map_get(x, key, data, callback) libcdsb_map_find (x, _LIBCDSB_value_pointer(key), _LIBCDSB_vtypeof(key), data, callback, 0)
|
||||||
#define map_update(x, key, value) libcdsb_map_update (x, _LIBCDSB_value_pointer(key), _LIBCDSB_vtypeof(key), _LIBCDSB_value_pointer(value), _LIBCDSB_vtypeof(value))
|
#define map_update(x, key, value) libcdsb_map_update (x, _LIBCDSB_value_pointer(key), _LIBCDSB_vtypeof(key), _LIBCDSB_value_pointer(value), _LIBCDSB_vtypeof(value), 0, 0)
|
||||||
#define map_inject(x, key, value) libcdsb_map_inject (x, _LIBCDSB_value_pointer(key), _LIBCDSB_vtypeof(key), _LIBCDSB_value_pointer(value), _LIBCDSB_vtypeof(value))
|
#define map_inject(x, key, value) libcdsb_map_inject (x, _LIBCDSB_value_pointer(key), _LIBCDSB_vtypeof(key), _LIBCDSB_value_pointer(value), _LIBCDSB_vtypeof(value), 0, 0)
|
||||||
#define map_foreach(x, data, callback) libcdsb_map_foreach (x, data, callback, RBFOREACH_UNSPECIFIED, 0)
|
#define map_foreach(x, data, callback) libcdsb_map_foreach(x, data, callback, RBFOREACH_UNSPECIFIED, 0)
|
||||||
#define map_remove(x, key) map_pop (x, key, 0, 0)
|
#define map_remove(x, key) map_pop (x, key, 0, 0)
|
||||||
|
|
||||||
#define in_map(x, key) (map_get(x, key, 0, 0) == 0)
|
#define in_map(x, key) (map_get(x, key, 0, 0) == 0)
|
||||||
|
|
||||||
/*#####################################################################################################################*/
|
/*#####################################################################################################################*/
|
||||||
|
|
||||||
extern bool libcdsb_map_update (vtype_map* x, const void* key, vtype key_type, const void* value, vtype value_type) Nonnull__(1);
|
extern bool libcdsb_map_update (vtype_map* x, const void* key, vtype key_type, const void* value, vtype value_type, void* data, map_access_callback) Nonnull__(1);
|
||||||
extern bool libcdsb_map_inject (vtype_map* x, const void* key, vtype key_type, const void* value, vtype value_type) Nonnull__(1);
|
extern bool libcdsb_map_inject (vtype_map* x, const void* key, vtype key_type, const void* value, vtype value_type, void* data, map_access_callback) Nonnull__(1);
|
||||||
extern int libcdsb_map_find (vtype_map* x, const void* key, vtype key_type, void* data, map_access_callback, bool cut) Nonnull__(1);
|
extern int libcdsb_map_find (vtype_map* x, const void* key, vtype key_type, void* data, map_access_callback, bool cut) Nonnull__(1);
|
||||||
extern int libcdsb_map_foreach(vtype_map* x, void* data, map_access_callback, rbforeach_t, bool flush) Nonnull__(1,3);
|
extern int libcdsb_map_foreach(vtype_map* x, void* data, map_access_callback, rbforeach_t, bool flush) Nonnull__(1,3);
|
||||||
|
|
||||||
#endif /* LIBCDSB_MAP_H */
|
#endif /* LIBCDSB_MAP_H */
|
||||||
|
|||||||
+4
-4
@@ -104,7 +104,7 @@ extern vtype_map map_copy (const vtype_map* s) Pure__
|
|||||||
extern vtype_set vset_copy (const vtype_set* s) Pure__ Warn_unused_result__ Nonnull__(1);
|
extern vtype_set vset_copy (const vtype_set* s) Pure__ Warn_unused_result__ Nonnull__(1);
|
||||||
extern vtype_dict dict_copy (const vtype_dict* s) Pure__ Warn_unused_result__ Nonnull__(1);
|
extern vtype_dict dict_copy (const vtype_dict* s) Pure__ Warn_unused_result__ Nonnull__(1);
|
||||||
extern vtype_list dict_copy_keys(const vtype_dict* s) Pure__ Warn_unused_result__ Nonnull__(1);
|
extern vtype_list dict_copy_keys(const vtype_dict* s) Pure__ Warn_unused_result__ Nonnull__(1);
|
||||||
#define map_copy_keys(s) vset_copy((vtype_set*)s)
|
#define map_copy_keys(s) vset_copy(_LIBCDSB_nothing(s))
|
||||||
|
|
||||||
inline vtype_string* string_duplicate (const vtype_string* s) Always_inline__ Warn_unused_result__ Nonnull__(1);
|
inline vtype_string* string_duplicate (const vtype_string* s) Always_inline__ Warn_unused_result__ Nonnull__(1);
|
||||||
extern vtype_array* array_duplicate (const vtype_array* s) Warn_unused_result__ Nonnull__(1);
|
extern vtype_array* array_duplicate (const vtype_array* s) Warn_unused_result__ Nonnull__(1);
|
||||||
@@ -113,7 +113,7 @@ extern vtype_map* map_duplicate (const vtype_map* s)
|
|||||||
extern vtype_set* vset_duplicate (const vtype_set* s) Warn_unused_result__ Nonnull__(1);
|
extern vtype_set* vset_duplicate (const vtype_set* s) Warn_unused_result__ Nonnull__(1);
|
||||||
extern vtype_dict* dict_duplicate (const vtype_dict* s) Warn_unused_result__ Nonnull__(1);
|
extern vtype_dict* dict_duplicate (const vtype_dict* s) Warn_unused_result__ Nonnull__(1);
|
||||||
extern vtype_list* dict_duplicate_keys(const vtype_dict* s) Warn_unused_result__ Nonnull__(1);
|
extern vtype_list* dict_duplicate_keys(const vtype_dict* s) Warn_unused_result__ Nonnull__(1);
|
||||||
#define map_duplicate_keys(s) vset_duplicate((vtype_set*)s)
|
#define map_duplicate_keys(s) vset_duplicate(_LIBCDSB_nothing(s))
|
||||||
|
|
||||||
inline void string_copy_init (vtype_string* x, const vtype_string* s) Always_inline__ Nonnull__(1,2);
|
inline void string_copy_init (vtype_string* x, const vtype_string* s) Always_inline__ Nonnull__(1,2);
|
||||||
extern void array_copy_init (vtype_array* x, const vtype_array* s) Nonnull__(1,2);
|
extern void array_copy_init (vtype_array* x, const vtype_array* s) Nonnull__(1,2);
|
||||||
@@ -122,7 +122,7 @@ extern void map_copy_init (vtype_map* x, const vtype_map* s)
|
|||||||
extern void vset_copy_init (vtype_set* x, const vtype_set* s) Nonnull__(1,2);
|
extern void vset_copy_init (vtype_set* x, const vtype_set* s) Nonnull__(1,2);
|
||||||
extern void dict_copy_init (vtype_dict* x, const vtype_dict* s) Nonnull__(1,2);
|
extern void dict_copy_init (vtype_dict* x, const vtype_dict* s) Nonnull__(1,2);
|
||||||
extern void dict_init_keys (vtype_list* x, const vtype_dict* s) Nonnull__(1,2);
|
extern void dict_init_keys (vtype_list* x, const vtype_dict* s) Nonnull__(1,2);
|
||||||
#define map_copy_init_keys(x, s) vset_duplicate(x, (vtype_set*)s)
|
#define map_copy_init_keys(x, s) vset_copy_init(x, _LIBCDSB_nothing(s))
|
||||||
|
|
||||||
inline void string_free(vtype_string* x) Always_inline__;
|
inline void string_free(vtype_string* x) Always_inline__;
|
||||||
extern void array_free (vtype_array* x);
|
extern void array_free (vtype_array* x);
|
||||||
@@ -144,7 +144,7 @@ inline size_t array_size (const vtype_array* x) { return x->size; }
|
|||||||
inline size_t dict_size (const vtype_dict* x) { return x->size; }
|
inline size_t dict_size (const vtype_dict* x) { return x->size; }
|
||||||
inline size_t dict_capacity(const vtype_dict* x) { return x->capacity; }
|
inline size_t dict_capacity(const vtype_dict* x) { return x->capacity; }
|
||||||
inline size_t string_nmemb (const vtype_string* x) { return (x->buffer) ? libcdsb_strlen(x->buffer) : 0; }
|
inline size_t string_nmemb (const vtype_string* x) { return (x->buffer) ? libcdsb_strlen(x->buffer) : 0; }
|
||||||
inline void string_free ( vtype_string* x) { libcdsb_free(x->buffer); x->buffer = 0; }
|
inline void string_free ( vtype_string* x) { if (x) { libcdsb_free(x->buffer); x->buffer = 0; } }
|
||||||
|
|
||||||
inline vtype_string string_copy(const vtype_string* s) {
|
inline vtype_string string_copy(const vtype_string* s) {
|
||||||
vtype_string x = { .buffer = libcdsb_strdup(s->buffer) };
|
vtype_string x = { .buffer = libcdsb_strdup(s->buffer) };
|
||||||
|
|||||||
@@ -5,6 +5,8 @@
|
|||||||
#include "../__internal/assert.h"
|
#include "../__internal/assert.h"
|
||||||
|
|
||||||
void array_free(arr_t* x) {
|
void array_free(arr_t* x) {
|
||||||
|
if (is_null(x)) return;
|
||||||
|
|
||||||
if (x->size && x->type >= VTYPE_STRING) {
|
if (x->size && x->type >= VTYPE_STRING) {
|
||||||
void* p = x->mem;
|
void* p = x->mem;
|
||||||
|
|
||||||
|
|||||||
@@ -4,6 +4,7 @@
|
|||||||
#include "include.h"
|
#include "include.h"
|
||||||
|
|
||||||
void dict_free(dict_t* x) {
|
void dict_free(dict_t* x) {
|
||||||
|
if (is_null(x)) return;
|
||||||
|
|
||||||
while (x->capacity--) {
|
while (x->capacity--) {
|
||||||
while (!is_null(x->nodes[x->capacity])) {
|
while (!is_null(x->nodes[x->capacity])) {
|
||||||
|
|||||||
+18
-89
@@ -50,7 +50,7 @@ bool libcdsb_dict_shrink_to_fit(dict_t* s) {
|
|||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
bool libcdsb_dict_update(dict_t* x, const void* k, vtype kt, const void* v, vtype vt) {
|
bool libcdsb_dict_update(dict_t* x, const void* k, vtype kt, const void* v, vtype vt, void* dt, dict_access_callback callback) {
|
||||||
dnode_t *c, **p;
|
dnode_t *c, **p;
|
||||||
|
|
||||||
if (!x->capacity || (double)x->size / x->capacity > REBUILD_POINT_MAX)
|
if (!x->capacity || (double)x->size / x->capacity > REBUILD_POINT_MAX)
|
||||||
@@ -60,10 +60,12 @@ bool libcdsb_dict_update(dict_t* x, const void* k, vtype kt, const void* v, vtyp
|
|||||||
|
|
||||||
while (!is_null(c)) {
|
while (!is_null(c)) {
|
||||||
if (vtype_compare(k, kt, vnode_peek(&c->key, c->key_type), c->key_type) == 0) {
|
if (vtype_compare(k, kt, vnode_peek(&c->key, c->key_type), c->key_type) == 0) {
|
||||||
|
if (!callback) callback(vnode_peek(&c->key, c->key_type), c->key_type,
|
||||||
|
vnode_peek(&c->value, c->value_type), c->value_type, dt);
|
||||||
|
|
||||||
vnode_free(&c->value, c->value_type);
|
vnode_free(&c->value, c->value_type);
|
||||||
|
|
||||||
c->value = vnode_create(v, vt);
|
c->value = vnode_create(v, c->value_type = vt);
|
||||||
c->value_type = vt;
|
|
||||||
|
|
||||||
return true;
|
return true;
|
||||||
} else c = c->prev;
|
} else c = c->prev;
|
||||||
@@ -71,11 +73,9 @@ bool libcdsb_dict_update(dict_t* x, const void* k, vtype kt, const void* v, vtyp
|
|||||||
|
|
||||||
c = malloc(sizeof(*c));
|
c = malloc(sizeof(*c));
|
||||||
|
|
||||||
c->prev = *p;
|
c->prev = *p;
|
||||||
c->key = vnode_create(k, kt);
|
c->key = vnode_create(k, c->key_type = kt);
|
||||||
c->value = vnode_create(v, vt);
|
c->value = vnode_create(v, c->value_type = vt);
|
||||||
c->key_type = kt;
|
|
||||||
c->value_type = vt;
|
|
||||||
|
|
||||||
*p = c;
|
*p = c;
|
||||||
++x->size;
|
++x->size;
|
||||||
@@ -84,7 +84,7 @@ bool libcdsb_dict_update(dict_t* x, const void* k, vtype kt, const void* v, vtyp
|
|||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
bool libcdsb_dict_inject(dict_t* x, const void* k, vtype kt, const void* v, vtype vt) {
|
bool libcdsb_dict_inject(dict_t* x, const void* k, vtype kt, const void* v, vtype vt, void* dt, dict_access_callback callback) {
|
||||||
dnode_t *c, **p;
|
dnode_t *c, **p;
|
||||||
|
|
||||||
if (!x->capacity || (double)x->size / x->capacity > REBUILD_POINT_MAX)
|
if (!x->capacity || (double)x->size / x->capacity > REBUILD_POINT_MAX)
|
||||||
@@ -94,93 +94,22 @@ bool libcdsb_dict_inject(dict_t* x, const void* k, vtype kt, const void* v, vtyp
|
|||||||
|
|
||||||
while (!is_null(c)) {
|
while (!is_null(c)) {
|
||||||
if (vtype_compare(k, kt, vnode_peek(&c->key, c->key_type), c->key_type) == 0) {
|
if (vtype_compare(k, kt, vnode_peek(&c->key, c->key_type), c->key_type) == 0) {
|
||||||
|
if (!callback) callback(vnode_peek(&c->key, c->key_type), c->key_type,
|
||||||
|
vnode_peek(&c->value, c->value_type), c->value_type, dt);
|
||||||
|
|
||||||
|
vnode_free(&c->key, c->key_type);
|
||||||
vnode_free(&c->value, c->value_type);
|
vnode_free(&c->value, c->value_type);
|
||||||
|
|
||||||
c->value = vnode_create(v, vt);
|
vnode_attach(&c->key, k, c->key_type = kt);
|
||||||
c->value_type = vt;
|
vnode_attach(&c->value, v, c->value_type = vt);
|
||||||
|
|
||||||
return true;
|
return true;
|
||||||
} else c = c->prev;
|
} else c = c->prev;
|
||||||
}
|
}
|
||||||
|
|
||||||
c = malloc(sizeof(*c));
|
(c = malloc(sizeof(*c)))->prev = *p;
|
||||||
|
vnode_attach(&c->key, k, c->key_type = kt);
|
||||||
c->prev = *p;
|
vnode_attach(&c->value, v, c->value_type = vt);
|
||||||
c->key_type = kt;
|
|
||||||
c->value_type = vt;
|
|
||||||
|
|
||||||
vnode_attach(&c->key, k, kt);
|
|
||||||
vnode_attach(&c->value, v, vt);
|
|
||||||
|
|
||||||
*p = c;
|
|
||||||
++x->size;
|
|
||||||
|
|
||||||
return false;
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
bool libcdsb_dict_inject_key(dict_t* x, const void* k, vtype kt, const void* v, vtype vt) {
|
|
||||||
dnode_t *c, **p;
|
|
||||||
|
|
||||||
if (!x->capacity || (double)x->size / x->capacity > REBUILD_POINT_MAX)
|
|
||||||
libcdsb_builtin_rehash(x, x->capacity + CAPACITY_BLOCK);
|
|
||||||
|
|
||||||
c = *(p = x->nodes + (vtype_hash(k, kt) % x->capacity));
|
|
||||||
|
|
||||||
while (!is_null(c)) {
|
|
||||||
if (vtype_compare(k, kt, vnode_peek(&c->key, c->key_type), c->key_type) == 0) {
|
|
||||||
vnode_free(&c->value, c->value_type);
|
|
||||||
|
|
||||||
c->value = vnode_create(v, vt);
|
|
||||||
c->value_type = vt;
|
|
||||||
|
|
||||||
return true;
|
|
||||||
} else c = c->prev;
|
|
||||||
}
|
|
||||||
|
|
||||||
c = malloc(sizeof(*c));
|
|
||||||
|
|
||||||
c->prev = *p;
|
|
||||||
c->value = vnode_create(v, vt);
|
|
||||||
c->key_type = kt;
|
|
||||||
c->value_type = vt;
|
|
||||||
|
|
||||||
vnode_attach(&c->key, k, kt);
|
|
||||||
|
|
||||||
*p = c;
|
|
||||||
++x->size;
|
|
||||||
|
|
||||||
return false;
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
bool libcdsb_dict_inject_value(dict_t* x, const void* k, vtype kt, const void* v, vtype vt) {
|
|
||||||
dnode_t *c, **p;
|
|
||||||
|
|
||||||
if (!x->capacity || (double)x->size / x->capacity > REBUILD_POINT_MAX)
|
|
||||||
libcdsb_builtin_rehash(x, x->capacity + CAPACITY_BLOCK);
|
|
||||||
|
|
||||||
c = *(p = x->nodes + (vtype_hash(k, kt) % x->capacity));
|
|
||||||
|
|
||||||
while (!is_null(c)) {
|
|
||||||
if (vtype_compare(k, kt, vnode_peek(&c->key, c->key_type), c->key_type) == 0) {
|
|
||||||
vnode_free(&c->value, c->value_type);
|
|
||||||
|
|
||||||
c->value = vnode_create(v, vt);
|
|
||||||
c->value_type = vt;
|
|
||||||
|
|
||||||
return true;
|
|
||||||
} else c = c->prev;
|
|
||||||
}
|
|
||||||
|
|
||||||
c = malloc(sizeof(*c));
|
|
||||||
|
|
||||||
c->prev = *p;
|
|
||||||
c->key = vnode_create(k, kt);
|
|
||||||
c->key_type = kt;
|
|
||||||
c->value_type = vt;
|
|
||||||
|
|
||||||
vnode_attach(&c->value, v, vt);
|
|
||||||
|
|
||||||
*p = c;
|
*p = c;
|
||||||
++x->size;
|
++x->size;
|
||||||
|
|||||||
@@ -7,6 +7,8 @@ void list_free(list_t* x) {
|
|||||||
lnode_t* c;
|
lnode_t* c;
|
||||||
lnode_t* next;
|
lnode_t* next;
|
||||||
|
|
||||||
|
if (is_null(x)) return;
|
||||||
|
|
||||||
c = x->first;
|
c = x->first;
|
||||||
|
|
||||||
while (!is_null(c)) {
|
while (!is_null(c)) {
|
||||||
|
|||||||
+10
-6
@@ -3,7 +3,7 @@
|
|||||||
|
|
||||||
#include "include.h"
|
#include "include.h"
|
||||||
|
|
||||||
bool libcdsb_list_insert(list_t* x, ssize_t i, const void* v, vtype t, int ins) {
|
bool libcdsb_list_insert(list_t* x, ssize_t i, const void* v, vtype t, int ins, void* dt, list_access_callback callback) {
|
||||||
|
|
||||||
ldir_t dir;
|
ldir_t dir;
|
||||||
lnode_t* c;
|
lnode_t* c;
|
||||||
@@ -41,8 +41,10 @@ bool libcdsb_list_insert(list_t* x, ssize_t i, const void* v, vtype t, int ins)
|
|||||||
} else ldir_inv((lnode_t*)x, dir) = c;
|
} else ldir_inv((lnode_t*)x, dir) = c;
|
||||||
|
|
||||||
ldir_dir(ldir_inv(c, dir), dir) = c;
|
ldir_dir(ldir_inv(c, dir), dir) = c;
|
||||||
|
} else {
|
||||||
} else vnode_free(&c->node, c->type);
|
if (callback) callback(vnode_peek(&c->node, c->type), -1, c->type, dt);
|
||||||
|
vnode_free(&c->node, c->type);
|
||||||
|
}
|
||||||
|
|
||||||
c->node = vnode_create(v, t);
|
c->node = vnode_create(v, t);
|
||||||
c->type = t;
|
c->type = t;
|
||||||
@@ -51,7 +53,7 @@ bool libcdsb_list_insert(list_t* x, ssize_t i, const void* v, vtype t, int ins)
|
|||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
bool libcdsb_list_attach(list_t* x, ssize_t i, const void* v, vtype t, int ins) {
|
bool libcdsb_list_attach(list_t* x, ssize_t i, const void* v, vtype t, int ins, void* dt, list_access_callback callback) {
|
||||||
|
|
||||||
ldir_t dir;
|
ldir_t dir;
|
||||||
lnode_t* c;
|
lnode_t* c;
|
||||||
@@ -89,8 +91,10 @@ bool libcdsb_list_attach(list_t* x, ssize_t i, const void* v, vtype t, int ins)
|
|||||||
} else ldir_inv((lnode_t*)x, dir) = c;
|
} else ldir_inv((lnode_t*)x, dir) = c;
|
||||||
|
|
||||||
ldir_dir(ldir_inv(c, dir), dir) = c;
|
ldir_dir(ldir_inv(c, dir), dir) = c;
|
||||||
|
} else {
|
||||||
} else vnode_free(&c->node, c->type);
|
if (callback) callback(vnode_peek(&c->node, c->type), -1, c->type, dt);
|
||||||
|
vnode_free(&c->node, c->type);
|
||||||
|
}
|
||||||
|
|
||||||
vnode_attach(&c->node, v, c->type = t);
|
vnode_attach(&c->node, v, c->type = t);
|
||||||
|
|
||||||
|
|||||||
@@ -12,6 +12,8 @@ void map_init(map_t* x, vtype t) {
|
|||||||
void map_free(map_t* x) {
|
void map_free(map_t* x) {
|
||||||
mnode_t *t, *c;
|
mnode_t *t, *c;
|
||||||
|
|
||||||
|
if (is_null(x)) return;
|
||||||
|
|
||||||
c = x->root;
|
c = x->root;
|
||||||
|
|
||||||
while (!mnode_is_empty(x->root)) {
|
while (!mnode_is_empty(x->root)) {
|
||||||
|
|||||||
+9
-4
@@ -3,7 +3,7 @@
|
|||||||
|
|
||||||
#include "include.h"
|
#include "include.h"
|
||||||
|
|
||||||
bool libcdsb_map_update(map_t* x, const void* k, vtype kt, const void* v, vtype vt) {
|
bool libcdsb_map_update(map_t* x, const void* k, vtype kt, const void* v, vtype vt, void* dt, map_access_callback callback) {
|
||||||
int cmp;
|
int cmp;
|
||||||
mnode_t* n;
|
mnode_t* n;
|
||||||
mnode_t* p;
|
mnode_t* p;
|
||||||
@@ -14,10 +14,12 @@ bool libcdsb_map_update(map_t* x, const void* k, vtype kt, const void* v, vtype
|
|||||||
cmp = vtype_compare(k, kt, vnode_peek(&n->key, kt), kt);
|
cmp = vtype_compare(k, kt, vnode_peek(&n->key, kt), kt);
|
||||||
|
|
||||||
if (cmp == 0) {
|
if (cmp == 0) {
|
||||||
|
if (callback) callback(vnode_peek(&n->key, x->type), x->type,
|
||||||
|
vnode_peek(&n->value, n->type), n->type, dt);
|
||||||
|
|
||||||
vnode_free(&n->value, n->type);
|
vnode_free(&n->value, n->type);
|
||||||
|
|
||||||
n->value = vnode_create(v, vt);
|
n->value = vnode_create(v, n->type = vt);
|
||||||
n->type = vt;
|
|
||||||
|
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
@@ -43,7 +45,7 @@ bool libcdsb_map_update(map_t* x, const void* k, vtype kt, const void* v, vtype
|
|||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
bool libcdsb_map_inject(map_t* x, const void* k, vtype kt, const void* v, vtype vt) {
|
bool libcdsb_map_inject(map_t* x, const void* k, vtype kt, const void* v, vtype vt, void* dt, map_access_callback callback) {
|
||||||
int cmp;
|
int cmp;
|
||||||
mnode_t* n;
|
mnode_t* n;
|
||||||
mnode_t* p;
|
mnode_t* p;
|
||||||
@@ -60,6 +62,9 @@ bool libcdsb_map_inject(map_t* x, const void* k, vtype kt, const void* v, vtype
|
|||||||
cmp = vtype_compare(k, kt, vnode_peek(&n->key, kt), kt);
|
cmp = vtype_compare(k, kt, vnode_peek(&n->key, kt), kt);
|
||||||
|
|
||||||
if (cmp == 0) {
|
if (cmp == 0) {
|
||||||
|
if (callback) callback(vnode_peek(&n->key, x->type), x->type,
|
||||||
|
vnode_peek(&n->value, n->type), n->type, dt);
|
||||||
|
|
||||||
vnode_free(&n->key, x->type);
|
vnode_free(&n->key, x->type);
|
||||||
vnode_free(&n->value, n->type);
|
vnode_free(&n->value, n->type);
|
||||||
|
|
||||||
|
|||||||
+95
@@ -0,0 +1,95 @@
|
|||||||
|
/* This software is licensed by the MIT License, see LICENSE file */
|
||||||
|
/* Copyright © 2022 Gregory Lirent */
|
||||||
|
|
||||||
|
#include <stdarg.h>
|
||||||
|
#include <stdlib.h>
|
||||||
|
#include "__internal/include.h"
|
||||||
|
#undef malloc
|
||||||
|
#undef free
|
||||||
|
|
||||||
|
void libcdsb_queue_init(queue_t* x) {
|
||||||
|
memset(x, 0, sizeof(*x));
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
void libcdsb_queue_push(queue_t* x, void* value) {
|
||||||
|
stack_t* n;
|
||||||
|
|
||||||
|
if (!(n = malloc(sizeof(*n))))
|
||||||
|
abort();
|
||||||
|
|
||||||
|
n->prev = 0;
|
||||||
|
|
||||||
|
if (!x->back) {
|
||||||
|
x->front = n;
|
||||||
|
x->back = n;
|
||||||
|
} else x->back->prev = n;
|
||||||
|
|
||||||
|
n->value = value;
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
void libcdsb_queue_push_many(queue_t* x, size_t c, ...) {
|
||||||
|
va_list args;
|
||||||
|
stack_t* n;
|
||||||
|
va_start(args, c);
|
||||||
|
|
||||||
|
if (c) {
|
||||||
|
|
||||||
|
if (!x->back) {
|
||||||
|
if (!(n = malloc(sizeof(*n))))
|
||||||
|
abort();
|
||||||
|
|
||||||
|
x->front = n;
|
||||||
|
x->back = n;
|
||||||
|
n->prev = 0;
|
||||||
|
n->value = va_arg(args, void*);
|
||||||
|
--c;
|
||||||
|
}
|
||||||
|
|
||||||
|
while (c--) {
|
||||||
|
if (!(n = malloc(sizeof(*n))))
|
||||||
|
abort();
|
||||||
|
|
||||||
|
x->back->prev = n;
|
||||||
|
n->prev = 0;
|
||||||
|
n->value = va_arg(args, void*);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
va_end(args);
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
void* libcdsb_queue_pop(queue_t* x) {
|
||||||
|
stack_t* n;
|
||||||
|
void* v;
|
||||||
|
|
||||||
|
if (x->front) {
|
||||||
|
n = x->front;
|
||||||
|
v = n->value;
|
||||||
|
|
||||||
|
if (!(x->front = n->prev)) {
|
||||||
|
x->back = 0;
|
||||||
|
}
|
||||||
|
|
||||||
|
free(n);
|
||||||
|
} else v = 0;
|
||||||
|
|
||||||
|
return v;
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
void libcdsb_queue_flush(queue_t* x) {
|
||||||
|
stack_t* c;
|
||||||
|
|
||||||
|
c = x->front;
|
||||||
|
|
||||||
|
while (x->front) {
|
||||||
|
c = x->front;
|
||||||
|
x->front = c->prev;
|
||||||
|
free(c);
|
||||||
|
}
|
||||||
|
|
||||||
|
x->back = 0;
|
||||||
|
}
|
||||||
+24
-40
@@ -196,60 +196,44 @@ void* libcdsb_builtin_rbtree_node_create(void* v, rbnode_t* p, int c, int n) {
|
|||||||
|
|
||||||
|
|
||||||
stack_t libcdsb_builtin_rbtree_iter_inorder(rbnode_t** root, bool reverse) {
|
stack_t libcdsb_builtin_rbtree_iter_inorder(rbnode_t** root, bool reverse) {
|
||||||
rbnode_t *n, hack;
|
stack_t z, *cur;
|
||||||
stack_t z, *bot;
|
rbnode_t *n;
|
||||||
|
|
||||||
memset(&z, 0, sizeof(z));
|
memset(&z, 0, sizeof(z));
|
||||||
|
|
||||||
if (rbnode_is_empty(*root))
|
if (rbnode_is_empty(n = *root))
|
||||||
return z;
|
return z;
|
||||||
|
|
||||||
hack.right = *root;
|
while (!rbnode_is_empty(n)) {
|
||||||
n = &hack;
|
stack_insert(&z, n);
|
||||||
|
n = n->left;
|
||||||
|
}
|
||||||
|
|
||||||
for (bot = &z;;) {
|
cur = z.prev;
|
||||||
for (;;) {
|
z.value = z.prev->value;
|
||||||
if (rbnode_is_empty(n->right)) {
|
z.prev = z.prev->prev;
|
||||||
|
|
||||||
if (rbnode_is_root(n->parent) || n->parent->left == n) {
|
free(cur);
|
||||||
n = n->parent;
|
|
||||||
break;
|
|
||||||
} else n = n->parent;
|
|
||||||
|
|
||||||
if (rbnode_is_root(n->parent) || n->parent->left == n) {
|
cur = &z;
|
||||||
n = n->parent;
|
|
||||||
break;
|
|
||||||
}
|
|
||||||
|
|
||||||
do {
|
while ((cur = cur->prev)) {
|
||||||
n = n->parent;
|
n = cur->value;
|
||||||
} while (n->parent->right == n);
|
|
||||||
|
|
||||||
n = n->parent;
|
if (!rbnode_is_empty(n->right)) {
|
||||||
} else {
|
n = n->right;
|
||||||
n = n->right;
|
|
||||||
|
|
||||||
while (!rbnode_is_empty(n->left))
|
while (!rbnode_is_empty(n)) {
|
||||||
n = n->left;
|
stack_insert(cur, n);
|
||||||
|
n = n->left;
|
||||||
break;
|
|
||||||
}
|
|
||||||
|
|
||||||
if (rbnode_is_root(n)) {
|
|
||||||
bot = z.prev;
|
|
||||||
z = *bot;
|
|
||||||
|
|
||||||
free(bot);
|
|
||||||
|
|
||||||
if (reverse)
|
|
||||||
stack_reverse(&z);
|
|
||||||
|
|
||||||
return z;
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
bot = stack_insert(bot, n);
|
|
||||||
}
|
}
|
||||||
|
|
||||||
|
if (reverse)
|
||||||
|
stack_reverse(&z);
|
||||||
|
|
||||||
|
return z;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
|||||||
@@ -12,6 +12,8 @@ void vset_init(set_t* x, vtype t) {
|
|||||||
void vset_free(set_t* x) {
|
void vset_free(set_t* x) {
|
||||||
rbnode_t *t, *c;
|
rbnode_t *t, *c;
|
||||||
|
|
||||||
|
if (is_null(x)) return;
|
||||||
|
|
||||||
c = x->root;
|
c = x->root;
|
||||||
|
|
||||||
while (!rbnode_is_empty(x->root)) {
|
while (!rbnode_is_empty(x->root)) {
|
||||||
|
|||||||
@@ -47,6 +47,7 @@ void libcdsb_stack_push_many(stack_t* x, size_t c, ...) {
|
|||||||
n->prev = x->prev;
|
n->prev = x->prev;
|
||||||
n->value = x->value;
|
n->value = x->value;
|
||||||
x->prev = n;
|
x->prev = n;
|
||||||
|
x->value = va_arg(args, void*);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
Reference in New Issue
Block a user