added HashMap_pushOrUpdate

This commit is contained in:
Timerix 2025-11-10 06:55:47 +05:00
parent 57c5942fcc
commit 0a1e87817d
2 changed files with 29 additions and 7 deletions

View File

@ -29,6 +29,8 @@ typedef struct HashMap_ {
#define HashMap_construct(PTR, T, VALUE_DESTRUCTOR) HashMap_construct_size(PTR, sizeof(T), VALUE_DESTRUCTOR)
void HashMap_construct_size(HashMap_* ptr, u32 value_t_size, FreeFunction NULLABLE(value_destructor));
void HashMap_destroy(HashMap_* ptr);
void* NULLABLE(HashMap_tryGetPtr)(HashMap_* ptr, str key);
bool HashMap_tryPush(HashMap_* ptr, str key, void* value_ptr);
bool HashMap_tryDelete(HashMap_* ptr, str key);
bool HashMap_tryPush(HashMap_* ptr, const str key, void* value_ptr);
void HashMap_pushOrUpdate(HashMap_* ptr, const str key, void* value_ptr);
NULLABLE(void*) HashMap_tryGetPtr(const HashMap_* ptr, const str key);
bool HashMap_tryDelete(HashMap_* ptr, const str key);

View File

@ -62,7 +62,7 @@ typedef struct BucketAndIndex {
///@returns `HashMapBucket*` for specified key or NULL, if table hasn't been allocated yet;
/// Index of existing item with the same key or -1 if no item is present.
static BucketAndIndex __HashMap_search(HashMap_* ptr, str key, u32 hash){
static BucketAndIndex __HashMap_search(const HashMap_* ptr, const str key, u32 hash){
if(ptr->height == 0)
return BucketAndIndex_null;
@ -79,7 +79,7 @@ static BucketAndIndex __HashMap_search(HashMap_* ptr, str key, u32 hash){
return r;
}
void* NULLABLE(HashMap_tryGetPtr)(HashMap_* ptr, str key){
void* HashMap_tryGetPtr(const HashMap_* ptr, const str key){
u32 hash = __HashMap_HASH_FUNC(key);
BucketAndIndex r = __HashMap_search(ptr, key, hash);
// key not found
@ -121,7 +121,7 @@ static void __HashMap_expand(HashMap_* ptr){
ptr->height_n = height_expanded_n;
}
bool HashMap_tryPush(HashMap_* ptr, str key, void* value_ptr){
bool HashMap_tryPush(HashMap_* ptr, const str key, void* value_ptr){
u32 hash = __HashMap_HASH_FUNC(key);
BucketAndIndex r = __HashMap_search(ptr, key, hash);
// found existing item with the same key
@ -140,7 +140,27 @@ bool HashMap_tryPush(HashMap_* ptr, str key, void* value_ptr){
return true;
}
bool HashMap_tryDelete(HashMap_* ptr, str key){
void HashMap_pushOrUpdate(HashMap_* ptr, const str key, void* value_ptr){
u32 hash = __HashMap_HASH_FUNC(key);
BucketAndIndex r = __HashMap_search(ptr, key, hash);
// found existing item with the same key
if(r.i != -1){
void* existing_item = ((u8*)r.bu->value_list.data) + r.i * ptr->value_t_size;
memcpy(existing_item, value_ptr, ptr->value_t_size);
}
HashMapBucket* bu = r.bu;
if(bu == NULL || List_len(&bu->key_hash_list, KeyHash) >= __HashMapBucket_MAX_LEN){
__HashMap_expand(ptr);
bu = &ptr->table[hash % ptr->height];
}
KeyHash kh = { .key = str_copy(key), .hash = hash };
List_push(&bu->key_hash_list, KeyHash, kh);
List_push_size(&bu->value_list, value_ptr, ptr->value_t_size);
}
bool HashMap_tryDelete(HashMap_* ptr, const str key){
u32 hash = __HashMap_HASH_FUNC(key);
BucketAndIndex r = __HashMap_search(ptr, key, hash);
// key not found