#ifndef ZH_VECTOR_H #define ZH_VECTOR_H #include #include #include /** * @brief Structure representing a dynamic vector. */ typedef struct { void **items; ///< Pointer to the array of items. uint16_t size; ///< Current number of elements in the vector. uint16_t capacity; ///< Current capacity of the vector. uint16_t unit; ///< Size of each element in bytes. bool status; ///< Indicates whether the vector is initialized. } zh_vector_t; #ifdef __cplusplus extern "C" { #endif /** * @brief Initializes a vector. * * @param vector Pointer to the vector to initialize. * @param unit Size of each element in bytes. * @return ESP_OK on success, or an error code otherwise. * * Example usage: * @code * zh_vector_t vector; * esp_err_t err = zh_vector_init(&vector, sizeof(int)); * if (err == ESP_OK) { * // Vector initialized successfully. * } * @endcode */ esp_err_t zh_vector_init(zh_vector_t *vector, uint16_t unit); /** * @brief Frees the memory allocated for the vector. * * @param vector Pointer to the vector to free. * @return ESP_OK on success, or an error code otherwise. * * Example usage: * @code * zh_vector_free(&vector); * @endcode */ esp_err_t zh_vector_free(zh_vector_t *vector); /** * @brief Adds an item to the end of the vector. * * @param vector Pointer to the vector. * @param item Pointer to the item to add. * @return ESP_OK on success, or an error code otherwise. * * Example usage: * @code * int value = 42; * zh_vector_push_back(&vector, &value); * @endcode */ esp_err_t zh_vector_push_back(zh_vector_t *vector, void *item); /** * @brief Adds an item to the end of the vector without copying its contents. * * This function directly assigns the provided pointer to the vector's internal storage, * avoiding the need to allocate memory or copy data. It is useful when the item is already * allocated and managed externally. * * @param vector Pointer to the vector. * @param item Pointer to the item to add. * @return ESP_OK on success, or an error code otherwise. * * Example usage: * @code * zh_vector_t vector; * zh_vector_init(&vector, sizeof(int)); * int *value = malloc(sizeof(int)); * *value = 42; * zh_vector_emplace_back(&vector, value); * @endcode */ esp_err_t zh_vector_emplace_back(zh_vector_t *vector, void *item); /** * @brief Removes the last item from the vector. * * @param vector Pointer to the vector. * @return ESP_OK on success, or an error code otherwise. * * Example usage: * @code * zh_vector_pop_back(&vector); * @endcode */ esp_err_t zh_vector_pop_back(zh_vector_t *vector); /** * @brief Gets the item at the specified index. * * @param vector Pointer to the vector. * @param index Index of the item to retrieve. * @return Pointer to the item, or NULL if the index is out of bounds. * * Example usage: * @code * int *item = (int *)zh_vector_get_item(&vector, 0); * if (item != NULL) { * // Use the item. * } * @endcode */ void *zh_vector_get_item(zh_vector_t *vector, uint16_t index); /** * @brief Checks if the vector is empty. * * @param vector Pointer to the vector. * @return true if the vector is empty, false otherwise. * * Example usage: * @code * if (zh_vector_is_empty(&vector)) { * // Vector is empty. * } * @endcode */ bool zh_vector_is_empty(zh_vector_t *vector); /** * @brief Clears all items from the vector. * * @param vector Pointer to the vector. * @return ESP_OK on success, or an error code otherwise. * * Example usage: * @code * zh_vector_clear(&vector); * @endcode */ esp_err_t zh_vector_clear(zh_vector_t *vector); /** * @brief Sorts the vector in ascending order. * * @param vector Pointer to the vector. * @param cmp Comparison function to compare items. * @return ESP_OK on success, or an error code otherwise. * * Example usage: * @code * int compare(const void *a, const void *b) { * return (*(int *)a - *(int *)b); * } * zh_vector_sort(&vector, compare); * @endcode */ esp_err_t zh_vector_sort(zh_vector_t *vector, int (*cmp)(const void *, const void *)); /** * @brief Finds the index of the specified item in the vector. * * @param vector Pointer to the vector. * @param item Pointer to the item to find. * @param cmp Comparison function to compare items. * @return Index of the found item, or -1 if the item is not found. * * Example usage: * @code * int value = 42; * int index = zh_vector_find(&vector, &value, compare); * if (index != -1) { * // Item found at index. * } * @endcode */ int zh_vector_find(zh_vector_t *vector, void *item, int (*cmp)(const void *, const void *)); /** * @brief Removes all occurrences of the specified item from the vector. * * @param vector Pointer to the vector. * @param item Pointer to the item to remove. * @param cmp Comparison function to compare items. * @return ESP_OK on success, or an error code otherwise. * * Example usage: * @code * int value = 42; * zh_vector_remove_all(&vector, &value, compare); * @endcode */ esp_err_t zh_vector_remove_all(zh_vector_t *vector, void *item, int (*cmp)(const void *, const void *)); /** * @brief Replaces all occurrences of an item in the vector with a new item. * * @param vector Pointer to the vector. * @param old_item Pointer to the item to replace. * @param new_item Pointer to the new item. * @param cmp Comparison function to compare items. * @return ESP_OK on success, or an error code otherwise. * * Example usage: * @code * int old_value = 42; * int new_value = 84; * zh_vector_replace_all(&vector, &old_value, &new_value, compare); * @endcode */ esp_err_t zh_vector_replace_all(zh_vector_t *vector, void *old_item, void *new_item, int (*cmp)(const void *, const void *)); /** * @brief Counts the number of items in the vector that satisfy a predicate. * * @param vector Pointer to the vector. * @param predicate Predicate function to evaluate items. * @return Number of items that satisfy the predicate. * * Example usage: * @code * bool is_even(const void *item) { * return (*(int *)item % 2) == 0; * } * uint16_t count = zh_vector_count_if(&vector, is_even); * @endcode */ uint16_t zh_vector_count_if(zh_vector_t *vector, bool (*predicate)(const void *)); /** * @brief Shuffles the elements of the vector randomly. * * @param vector Pointer to the vector. * @return ESP_OK on success, or an error code otherwise. * * Example usage: * @code * zh_vector_shuffle(&vector); * @endcode */ esp_err_t zh_vector_shuffle(zh_vector_t *vector); /** * @brief Finds the minimum item in the vector. * * @param vector Pointer to the vector. * @param cmp Comparison function to compare items. * @return Pointer to the minimum item, or NULL if the vector is empty. * * Example usage: * @code * int *min_item = (int *)zh_vector_min(&vector, compare); * if (min_item != NULL) { * // Use the minimum item. * } * @endcode */ void *zh_vector_min(zh_vector_t *vector, int (*cmp)(const void *, const void *)); /** * @brief Finds the maximum item in the vector. * * @param vector Pointer to the vector. * @param cmp Comparison function to compare items. * @return Pointer to the maximum item, or NULL if the vector is empty. * * Example usage: * @code * int *max_item = (int *)zh_vector_max(&vector, compare); * if (max_item != NULL) { * // Use the maximum item. * } * @endcode */ void *zh_vector_max(zh_vector_t *vector, int (*cmp)(const void *, const void *)); /** * @brief Rotates the vector to the left by the specified number of positions. * * @param vector Pointer to the vector. * @param positions Number of positions to rotate. * @return ESP_OK on success, or an error code otherwise. * * Example usage: * @code * zh_vector_rotate_left(&vector, 3); * @endcode */ esp_err_t zh_vector_rotate_left(zh_vector_t *vector, uint16_t positions); /** * @brief Rotates the vector to the right by the specified number of positions. * * @param vector Pointer to the vector. * @param positions Number of positions to rotate. * @return ESP_OK on success, or an error code otherwise. * * Example usage: * @code * zh_vector_rotate_right(&vector, 2); * @endcode */ esp_err_t zh_vector_rotate_right(zh_vector_t *vector, uint16_t positions); /** * @brief Removes all items from the vector that satisfy a predicate. * * @param vector Pointer to the vector. * @param predicate Predicate function to evaluate items. * @return ESP_OK on success, or an error code otherwise. */ esp_err_t zh_vector_remove_if(zh_vector_t *vector, bool (*predicate)(const void *)); /** * @brief Removes all items from the vector that do not satisfy a predicate. * * @param vector Pointer to the vector. * @param predicate Predicate function to evaluate items. * @return ESP_OK on success, or an error code otherwise. */ esp_err_t zh_vector_remove_if_not(zh_vector_t *vector, bool (*predicate)(const void *)); /** * @brief Replaces items in the vector that satisfy a predicate with a new item. * * @param vector Pointer to the vector. * @param predicate Predicate function to evaluate items. * @param new_item Pointer to the new item to replace with. * @return ESP_OK on success, or an error code otherwise. */ esp_err_t zh_vector_replace(zh_vector_t *vector, bool (*predicate)(const void *), void *new_item); /** * @brief Merges the source vector into the destination vector. * * @param dest Pointer to the destination vector. * @param src Pointer to the source vector. * @return ESP_OK on success, or an error code otherwise. */ esp_err_t zh_vector_merge(zh_vector_t *dest, const zh_vector_t *src); /** * @brief Removes duplicate items from the vector using a comparison function. * * @param vector Pointer to the vector. * @param cmp Comparison function to compare items. * @return ESP_OK on success, or an error code otherwise. */ esp_err_t zh_vector_unique(zh_vector_t *vector, int (*cmp)(const void *, const void *)); /** * @brief Converts the vector to an array of pointers. * * @param vector Pointer to the vector. * @return Pointer to the array of pointers, or NULL on failure. */ void **zh_vector_to_array(zh_vector_t *vector); /** * @brief Partitions the vector into two parts based on a predicate. * * @param vector Pointer to the vector. * @param predicate Predicate function to evaluate items. * @param true_part Pointer to the vector to store items satisfying the predicate. * @param false_part Pointer to the vector to store items not satisfying the predicate. * @return ESP_OK on success, or an error code otherwise. */ esp_err_t zh_vector_partition(zh_vector_t *vector, bool (*predicate)(const void *), zh_vector_t *true_part, zh_vector_t *false_part); /** * @brief Copies items from the source vector to the destination vector that satisfy a predicate. * * @param src Pointer to the source vector. * @param dest Pointer to the destination vector. * @param predicate Predicate function to evaluate items. * @return ESP_OK on success, or an error code otherwise. */ esp_err_t zh_vector_copy_if(const zh_vector_t *src, zh_vector_t *dest, bool (*predicate)(const void *)); /** * @brief Rotates the vector by the specified number of positions. * * @param vector Pointer to the vector. * @param positions Number of positions to rotate (positive for right, negative for left). * @return ESP_OK on success, or an error code otherwise. */ esp_err_t zh_vector_rotate(zh_vector_t *vector, int16_t positions); /** * @brief Finds all items in the vector that match a predicate and returns their indices. * * @param vector Pointer to the vector. * @param predicate Predicate function to evaluate items. * @param indices Pointer to an array of indices (allocated dynamically). * @param count Pointer to store the number of found indices. * @return ESP_OK on success, or an error code otherwise. */ esp_err_t zh_vector_find_all(zh_vector_t *vector, bool (*predicate)(const void *), uint16_t **indices, uint16_t *count); /** * @brief Finds the intersection of two vectors and stores the result in a third vector. * * @param vector1 Pointer to the first vector. * @param vector2 Pointer to the second vector. * @param result Pointer to the vector to store the intersection. * @param cmp Comparison function to compare items. * @return ESP_OK on success, or an error code otherwise. */ esp_err_t zh_vector_intersect(const zh_vector_t *vector1, const zh_vector_t *vector2, zh_vector_t *result, int (*cmp)(const void *, const void *)); /** * @brief Finds the union of two vectors and stores the result in a third vector. * * @param vector1 Pointer to the first vector. * @param vector2 Pointer to the second vector. * @param result Pointer to the vector to store the union. * @param cmp Comparison function to compare items. * @return ESP_OK on success, or an error code otherwise. */ esp_err_t zh_vector_union(const zh_vector_t *vector1, const zh_vector_t *vector2, zh_vector_t *result, int (*cmp)(const void *, const void *)); /** * @brief Finds the difference of two vectors and stores the result in a third vector. * * @param vector1 Pointer to the first vector. * @param vector2 Pointer to the second vector. * @param result Pointer to the vector to store the difference. * @param cmp Comparison function to compare items. * @return ESP_OK on success, or an error code otherwise. */ esp_err_t zh_vector_difference(const zh_vector_t *vector1, const zh_vector_t *vector2, zh_vector_t *result, int (*cmp)(const void *, const void *)); /** * @brief Finds the symmetric difference of two vectors and stores the result in a third vector. * * @param vector1 Pointer to the first vector. * @param vector2 Pointer to the second vector. * @param result Pointer to the vector to store the symmetric difference. * @param cmp Comparison function to compare items. * @return ESP_OK on success, or an error code otherwise. */ esp_err_t zh_vector_symmetric_difference(const zh_vector_t *vector1, const zh_vector_t *vector2, zh_vector_t *result, int (*cmp)(const void *, const void *)); /** * @brief Gets the current size (number of elements) of the vector. * * @param vector Pointer to the vector. * @return The size of the vector, or -1 if the vector is not initialized or invalid. * * Example usage: * @code * zh_vector_t vector; * zh_vector_init(&vector, sizeof(int)); * int size = zh_vector_get_size(&vector); * printf("Vector size: %d\n", size); * @endcode */ esp_err_t zh_vector_get_size(zh_vector_t *vector); /** * @brief Adds an item to the end of the vector without copying its contents. * * This function directly assigns the provided pointer to the vector's internal storage, * avoiding the need to allocate memory or copy data. It is useful when the item is already * allocated and managed externally. * * @param vector Pointer to the vector. * @param item Pointer to the item to add. * @return ESP_OK on success, or an error code otherwise. * * Example usage: * @code * zh_vector_t vector; * zh_vector_init(&vector, sizeof(int)); * int *value = malloc(sizeof(int)); * *value = 42; * zh_vector_emplace_back(&vector, value); * @endcode */ esp_err_t zh_vector_emplace_back(zh_vector_t *vector, void *item); #ifdef __cplusplus } #endif #endif // ZH_VECTOR_H