archeus/src/std/vector.c

110 lines
2.9 KiB
C
Raw Normal View History

2022-10-27 15:16:54 -06:00
#include "arc/std/vector.h"
#include "arc/std/errno.h"
#include <stdlib.h>
#include <stdint.h>
#include <string.h>
struct ARC_Vector {
uint32_t *currentSize, *capacity;
void **data;
2022-10-27 15:16:54 -06:00
};
void ARC_Vector_Create(ARC_Vector **vector){
2022-10-27 15:16:54 -06:00
*vector = (ARC_Vector *) malloc(sizeof(ARC_Vector));
(*vector)->currentSize = (uint32_t *)malloc(sizeof(uint32_t));
(*vector)->capacity = (uint32_t *)malloc(sizeof(uint32_t));
(*vector)->data = (void **)malloc(sizeof(void *));
*(*vector)->currentSize = 0;
*(*vector)->capacity = 1;
2022-10-27 15:16:54 -06:00
}
void ARC_Vector_Destroy(ARC_Vector *vector){
free(vector->currentSize);
free(vector->capacity);
free(vector->data);
free(vector);
}
void ARC_Vector_Add(ARC_Vector *vector, void *data){
if(*vector->currentSize == ~((uint32_t)0)){
2022-10-27 15:16:54 -06:00
arc_errno = ARC_ERRNO_OVERFLOW;
return;
}
if(*vector->currentSize == *vector->capacity){
if(!*vector->capacity){
++*vector->capacity;
}
*vector->capacity <<= 1;
2022-10-27 15:16:54 -06:00
vector->data = (void *)realloc(vector->data, sizeof(void *) * *vector->capacity);
2022-10-27 15:16:54 -06:00
}
vector->data[*vector->currentSize] = data;
2022-10-27 15:16:54 -06:00
++*(vector->currentSize);
}
//this function removes the redundant checking currentSize and index that would happen if ARC_Vector_Remove called ARC_Vector_RemoveIndex
void ARC_Vector_RemoveIndexNoCheck(ARC_Vector *vector, uint32_t *index);
2022-10-27 15:16:54 -06:00
void ARC_Vector_Remove(ARC_Vector *vector, void *data, ARC_Vector_CompareDataFn compare){
if(!*vector->currentSize){
2022-10-27 15:16:54 -06:00
arc_errno = ARC_ERRNO_DATA;
return;
}
for(uint32_t i = 0; i < *vector->currentSize; i++){
if(!compare(data, vector->data[i])){
ARC_Vector_RemoveIndexNoCheck(vector, &i);
2022-10-27 15:16:54 -06:00
return;
}
}
//no matching data found in compare function
2022-10-27 15:16:54 -06:00
arc_errno = ARC_ERRNO_DATA;
}
void ARC_Vector_RemoveIndex(ARC_Vector *vector, uint32_t *index){
if(!*vector->currentSize || *index >= *vector->currentSize){
2022-10-27 15:16:54 -06:00
arc_errno = ARC_ERRNO_DATA;
return;
}
ARC_Vector_RemoveIndexNoCheck(vector, index);
}
void ARC_Vector_RemoveIndexNoCheck(ARC_Vector *vector, uint32_t *index){
for(uint32_t i = *index; i <= *vector->currentSize; i++){
if(i + 1 >= *vector->currentSize - 1){
break;
}
vector->data[i] = vector->data[i + 1];
}
--*vector->currentSize;
if(*vector->currentSize != *vector->capacity >> 1){
2022-10-27 15:16:54 -06:00
return;
}
*vector->capacity >>= 1;
if(*vector->capacity <= 0){
*vector->capacity = 1;
}
vector->data = (void *)realloc(vector->data, sizeof(void *) * *vector->capacity);
}
2022-10-27 15:16:54 -06:00
uint32_t *ARC_Vector_Size(ARC_Vector *vector){
return vector->currentSize;
2022-10-27 15:16:54 -06:00
}
void *ARC_Vector_Get(ARC_Vector *vector, uint32_t *index){
if(*index >= *vector->currentSize){
return NULL;
}
2022-10-27 15:16:54 -06:00
return vector->data[*index];
2024-02-08 02:48:08 -07:00
}