mirror of
				https://github.com/theoludwig/libcproject.git
				synced 2025-05-21 23:21:15 +02:00 
			
		
		
		
	feat!: remove dictionary data structure
				
					
				
			Replaced by `hash_map`
This commit is contained in:
		| @@ -20,7 +20,7 @@ | ||||
|  | ||||
| C is a low-level programming language and we often end up reinventing the wheel as the C standard library (`libc`) is quite small and in my humble opinion, not well designed. | ||||
|  | ||||
| **libcproject** solve this by providing common functions or data structures (`dictionary`, `linked_list`, `queue`, `stack`, etc.) we might need in our C projects. | ||||
| **libcproject** solve this by providing common functions or data structures (`hash_map`, `array_list`, `linked_list`, `queue`, `stack`, etc.) we might need in our C projects. | ||||
|  | ||||
| [Online documentation](https://libcproject.vercel.app/). | ||||
|  | ||||
|   | ||||
| @@ -1,64 +0,0 @@ | ||||
| #include "dictionary.h" | ||||
|  | ||||
| struct dictionary *dictionary_initialization() { | ||||
|   struct dictionary *dictionary = malloc(sizeof(struct dictionary)); | ||||
|   dictionary->items = malloc(sizeof(struct dictionary_item *) * DICTIONARY_INITIAL_CAPACITY); | ||||
|   dictionary->length = 0; | ||||
|   dictionary->capacity = DICTIONARY_INITIAL_CAPACITY; | ||||
|   for (size_t index = 0; index < dictionary->capacity; index++) { | ||||
|     dictionary->items[index] = NULL; | ||||
|   } | ||||
|   return dictionary; | ||||
| } | ||||
|  | ||||
| void dictionary_add(struct dictionary *dictionary, char *key, void *data) { | ||||
|   if (dictionary->length == dictionary->capacity) { | ||||
|     size_t previous_capacity = dictionary->capacity; | ||||
|     dictionary->capacity += DICTIONARY_INITIAL_CAPACITY; | ||||
|     dictionary->items = realloc(dictionary->items, sizeof(struct dictionary_item *) * dictionary->capacity); | ||||
|     for (size_t index = previous_capacity; index < dictionary->capacity; index++) { | ||||
|       dictionary->items[index] = NULL; | ||||
|     } | ||||
|   } | ||||
|   struct dictionary_item *item = NULL; | ||||
|   for (size_t index = 0; index < dictionary->length && item == NULL; index++) { | ||||
|     if (string_equals(key, dictionary->items[index]->key)) { | ||||
|       item = dictionary->items[index]; | ||||
|     } | ||||
|   } | ||||
|   if (item == NULL) { | ||||
|     item = malloc(sizeof(struct dictionary_item)); | ||||
|     item->key = key; | ||||
|     item->data = data; | ||||
|     dictionary->items[dictionary->length] = item; | ||||
|     dictionary->length++; | ||||
|   } else { | ||||
|     item->data = data; | ||||
|   } | ||||
| } | ||||
|  | ||||
| void dictionary_remove(struct dictionary *dictionary, char *key) { | ||||
|   bool found = false; | ||||
|   for (size_t index = 0; index < dictionary->length && !found; index++) { | ||||
|     if (string_equals(key, dictionary->items[index]->key)) { | ||||
|       free(dictionary->items[index]); | ||||
|       dictionary->items[index] = dictionary->items[dictionary->length - 1]; | ||||
|       dictionary->length--; | ||||
|       found = true; | ||||
|     } | ||||
|   } | ||||
| } | ||||
|  | ||||
| struct dictionary_item *dictionary_get(struct dictionary *dictionary, char *key) { | ||||
|   for (size_t index = 0; index < dictionary->length; index++) { | ||||
|     struct dictionary_item *item = dictionary->items[index]; | ||||
|     if (string_equals(key, item->key)) { | ||||
|       return item; | ||||
|     } | ||||
|   } | ||||
|   return NULL; | ||||
| } | ||||
|  | ||||
| bool dictionary_contains_key(struct dictionary *dictionary, char *key) { | ||||
|   return dictionary_get(dictionary, key) != NULL; | ||||
| } | ||||
| @@ -1,35 +0,0 @@ | ||||
| #ifndef __LIBCPROJECT_DICTIONARY__ | ||||
| #define __LIBCPROJECT_DICTIONARY__ | ||||
|  | ||||
| #include <stdbool.h> | ||||
| #include <stdlib.h> | ||||
|  | ||||
| #include "string.h" | ||||
| #include "types.h" | ||||
|  | ||||
| #define DICTIONARY_INITIAL_CAPACITY 10 | ||||
|  | ||||
| // Dictionary implementation with O(n) lookup complexity. | ||||
| struct dictionary { | ||||
|   struct dictionary_item **items; | ||||
|  | ||||
|   size_t length; | ||||
|   size_t capacity; | ||||
| }; | ||||
|  | ||||
| struct dictionary_item { | ||||
|   void *data; | ||||
|   char *key; | ||||
| }; | ||||
|  | ||||
| struct dictionary *dictionary_initialization(); | ||||
|  | ||||
| void dictionary_add(struct dictionary *dictionary, char *key, void *data); | ||||
|  | ||||
| void dictionary_remove(struct dictionary *dictionary, char *key); | ||||
|  | ||||
| struct dictionary_item *dictionary_get(struct dictionary *dictionary, char *key); | ||||
|  | ||||
| bool dictionary_contains_key(struct dictionary *dictionary, char *key); | ||||
|  | ||||
| #endif | ||||
| @@ -94,22 +94,6 @@ void terminal_print_linked_list(struct linked_list* linked_list, void (*print_el | ||||
|   printf("NULL\n"); | ||||
| } | ||||
|  | ||||
| void terminal_print_dictionary(struct dictionary* dictionary, void (*print_element)(void*)) { | ||||
|   if (dictionary == NULL) { | ||||
|     exit(EXIT_FAILURE); | ||||
|   } | ||||
|   printf("{\n"); | ||||
|   for (size_t index = 0; index < dictionary->length; index++) { | ||||
|     struct dictionary_item* item = dictionary->items[index]; | ||||
|     printf("\t\""); | ||||
|     terminal_print_string(item->key); | ||||
|     printf("\" -> "); | ||||
|     print_element(&item->data); | ||||
|     printf("\n"); | ||||
|   } | ||||
|   printf("}\n"); | ||||
| } | ||||
|  | ||||
| void terminal_print_hash_map(struct hash_map* hash_map, void (*print_element)(void*)) { | ||||
|   if (hash_map == NULL) { | ||||
|     exit(EXIT_FAILURE); | ||||
|   | ||||
| @@ -7,7 +7,6 @@ | ||||
| #include <stdlib.h> | ||||
|  | ||||
| #include "character.h" | ||||
| #include "dictionary.h" | ||||
| #include "hash_map.h" | ||||
| #include "linked_list.h" | ||||
| #include "queue.h" | ||||
| @@ -98,15 +97,6 @@ void terminal_print_queue(struct queue* queue, void (*print_element)(void*)); | ||||
|  */ | ||||
| void terminal_print_linked_list(struct linked_list* linked_list, void (*print_element)(void*)); | ||||
|  | ||||
| /** | ||||
|  * @brief Print a dictionary. | ||||
|  * | ||||
|  * @param dictionary | ||||
|  * @param print_element | ||||
|  * @since v1.0.0 | ||||
|  */ | ||||
| void terminal_print_dictionary(struct dictionary* dictionary, void (*print_element)(void*)); | ||||
|  | ||||
| /** | ||||
|  * @brief Print a hash map. | ||||
|  * | ||||
|   | ||||
| @@ -4,7 +4,6 @@ | ||||
| #include "lib/array_list.h" | ||||
| #include "lib/character.h" | ||||
| #include "lib/convert.h" | ||||
| #include "lib/dictionary.h" | ||||
| #include "lib/filesystem.h" | ||||
| #include "lib/hash_map.h" | ||||
| #include "lib/linked_list.h" | ||||
|   | ||||
| @@ -1,27 +0,0 @@ | ||||
| #include "dictionary_test.h" | ||||
|  | ||||
| void dictionary_test() { | ||||
|   struct dictionary *dictionary = dictionary_initialization(); | ||||
|   assert(dictionary->length == 0); | ||||
|   dictionary_add(dictionary, "key", (void *)'a'); | ||||
|   dictionary_add(dictionary, "key1", (void *)'b'); | ||||
|   dictionary_add(dictionary, "key2", (void *)'c'); | ||||
|   dictionary_add(dictionary, "key3", (void *)'d'); | ||||
|   dictionary_add(dictionary, "key4", (void *)'e'); | ||||
|   dictionary_add(dictionary, "key5", (void *)'f'); | ||||
|   assert(dictionary->length == 6); | ||||
|   assert(dictionary_get(dictionary, "key")->data == (void *)'a'); | ||||
|   assert(dictionary_get(dictionary, "key1")->data == (void *)'b'); | ||||
|   assert(dictionary_get(dictionary, "key2")->data == (void *)'c'); | ||||
|   assert(dictionary_get(dictionary, "key3")->data == (void *)'d'); | ||||
|   assert(dictionary_get(dictionary, "key4")->data == (void *)'e'); | ||||
|   assert(dictionary_get(dictionary, "key5")->data == (void *)'f'); | ||||
|   dictionary_add(dictionary, "key5", (void *)'a'); | ||||
|   assert(dictionary_get(dictionary, "key5")->data == (void *)'a'); | ||||
|   assert(dictionary_contains_key(dictionary, "key5")); | ||||
|   assert(!dictionary_contains_key(dictionary, "invalid key")); | ||||
|   assert(dictionary_contains_key(dictionary, "key5")); | ||||
|   dictionary_remove(dictionary, "key5"); | ||||
|   assert(dictionary->length == 5); | ||||
|   assert(!dictionary_contains_key(dictionary, "key5")); | ||||
| } | ||||
| @@ -1,12 +0,0 @@ | ||||
| #ifndef __DICTIONARY_TEST__ | ||||
| #define __DICTIONARY_TEST__ | ||||
|  | ||||
| #include <assert.h> | ||||
| #include <stdio.h> | ||||
| #include <stdlib.h> | ||||
|  | ||||
| #include "libcproject.h" | ||||
|  | ||||
| void dictionary_test(); | ||||
|  | ||||
| #endif | ||||
| @@ -4,7 +4,6 @@ | ||||
| #include "array_list_test.h" | ||||
| #include "character_test.h" | ||||
| #include "convert_test.h" | ||||
| #include "dictionary_test.h" | ||||
| #include "hash_map_test.h" | ||||
| #include "linked_list_test.h" | ||||
| #include "mathematics_test.h" | ||||
| @@ -16,7 +15,6 @@ int main() { | ||||
|   array_list_test(); | ||||
|   character_test(); | ||||
|   convert_test(); | ||||
|   dictionary_test(); | ||||
|   hash_map_test(); | ||||
|   linked_list_test(); | ||||
|   mathematics_test(); | ||||
|   | ||||
		Reference in New Issue
	
	Block a user