pvjc24/cv4/list-ops/.meta/example.c
2024-03-07 20:52:21 +01:00

135 lines
2.9 KiB
C

#include "list_ops.h"
#include <string.h>
list_t *new_list(size_t length, list_element_t elements[])
{
list_t *list = malloc(sizeof(*list) + sizeof(list_element_t) * length);
if (!list)
return NULL;
list->length = length;
memcpy(list->elements, elements, sizeof(list_element_t) * length);
return list;
}
list_t *append_list(list_t *list1, list_t *list2)
{
if (!list1 || !list2)
return NULL;
size_t length = list1->length + list2->length;
list_t *list = malloc(sizeof(*list) + sizeof(list_element_t) * (length));
if (!list)
return NULL;
list->length = length;
if (length) {
memcpy(list->elements, list1->elements,
sizeof(list_element_t) * list1->length);
memcpy(&(list->elements[list1->length]), list2->elements,
sizeof(list_element_t) * list2->length);
}
return list;
}
list_t *filter_list(list_t *list, bool (*filter)(list_element_t))
{
if (!list || !filter)
return NULL;
list_t *filtered =
malloc(sizeof(*list) + sizeof(list_element_t) * list->length);
if (!filtered)
return NULL;
size_t j = 0;
for (size_t i = 0; i < list->length && j < list->length; ++i) {
if (filter(list->elements[i]))
filtered->elements[j++] = list->elements[i];
}
filtered->length = j;
return filtered;
}
size_t length_list(list_t *list)
{
if (!list)
return 0;
return list->length;
}
list_t *map_list(list_t *list, list_element_t (*map)(list_element_t))
{
if (!list || !map)
return NULL;
list_t *mapped =
malloc(sizeof(*list) + sizeof(list_element_t) * list->length);
if (!mapped)
return NULL;
mapped->length = list->length;
for (size_t i = 0; i < mapped->length; ++i)
mapped->elements[i] = map(list->elements[i]);
return mapped;
}
list_element_t foldl_list(list_t *list, list_element_t initial,
list_element_t (*foldl)(list_element_t,
list_element_t))
{
if (!list || !foldl)
return 0;
for (size_t i = 0; i < list->length; ++i)
initial = foldl(list->elements[i], initial);
return initial;
}
list_element_t foldr_list(list_t *list, list_element_t initial,
list_element_t (*foldr)(list_element_t,
list_element_t))
{
if (!list || !foldr)
return 0;
for (size_t i = list->length; i > 0; --i)
initial = foldr(list->elements[i - 1], initial);
return initial;
}
list_t *reverse_list(list_t *list)
{
if (!list)
return NULL;
list_t *reversed =
malloc(sizeof(*list) + sizeof(list_element_t) * list->length);
if (!reversed)
return NULL;
reversed->length = list->length;
for (size_t i = 0, j = reversed->length - 1; i < reversed->length;
i++, j--) {
reversed->elements[i] = list->elements[j];
}
return reversed;
}
void delete_list(list_t *list)
{
free(list);
}