diff --git a/.clang-tidy b/.clang-tidy deleted file mode 100644 index 0b0f492..0000000 --- a/.clang-tidy +++ /dev/null @@ -1,22 +0,0 @@ ---- -Checks: > - -*, - bugprone-*, - concurrency-*, - misc-*, - modernize-*, - performance-*, - readability-*, - portability-*, - -readability-braces-around-statements, - -readability-implicit-bool-conversion - -WarningsAsErrors: "" - -CheckOptions: - - key: readability-identifier-naming.VariableCase - value: lower_case - - key: readability-identifier-naming.FunctionCase - value: lower_case ---- - \ No newline at end of file diff --git a/CMakeLists.txt b/CMakeLists.txt index 7564e3b..9528c67 100644 --- a/CMakeLists.txt +++ b/CMakeLists.txt @@ -8,6 +8,7 @@ include_directories(include) set(SOURCES src/main.c src/char.c + src/utils.c ) add_executable(libvec ${SOURCES}) diff --git a/include/char.h b/include/char.h index e6e1bd6..b9dc65f 100644 --- a/include/char.h +++ b/include/char.h @@ -8,29 +8,32 @@ #ifndef CHAR_H #define CHAR_H -#define CAPACITY 1024 - #include #include #include #include #include +#include typedef struct { char* arr; size_t size; size_t capacity; + size_t max_size; } Vec8_t; -__attribute__((overloadable)) Vec8_t -create(const Vec8_t* input); - -__attribute__((overloadable)) Vec8_t -create(const _Bool init); +Vec8_t +create(const char* buf, const int len); Vec8_t -reserve(Vec8_t* ptr, size_t max_size); +push_back(Vec8_t* vec, const char val); + +Vec8_t +pop_back(Vec8_t* vec); + +Vec8_t +reserve(Vec8_t* ptr, const size_t max_size); Vec8_t shrink_to_fit(Vec8_t* ptr); @@ -41,10 +44,13 @@ swap(Vec8_t* ptr, Vec8_t* ptr_other); char* data(const Vec8_t* ptr); +size_t +capacity(const Vec8_t* ptr); + size_t max_size(const Vec8_t* ptr); -void delete (Vec8_t* vec); +void delete (const Vec8_t* vec); Vec8_t clear(Vec8_t* vec); @@ -76,12 +82,6 @@ back(const Vec8_t* vec); int empty(const Vec8_t* vec); -Vec8_t -add_back(Vec8_t* vec, char val); - -Vec8_t -pop_back(Vec8_t* vec); - __attribute__((overloadable)) Vec8_t resize(Vec8_t* vec, size_t size); diff --git a/include/utils.h b/include/utils.h new file mode 100644 index 0000000..48d81d3 --- /dev/null +++ b/include/utils.h @@ -0,0 +1,27 @@ +#ifndef UTILS_H +#define UTILS_H + +#include +#include +#define CAPACITY 1024 +#define SUCCESS 0 + +#define FAILURE 1 +#define ERR_ALLOC_FAIL 20 +#define ERR_BUF_NULL 21 +#define ERR_BAD_TYPE 22 +#define ERR_INVALID_SIZE 23 +#define ERR_VECTOR_NULL 24 +#define ERR_MAX_PASSED 25 + +extern const char* error_messages[]; + +#define LOG(msg) printf("LOG: %s\n", msg) /**< Print log message*/ +#define LOGERROR(error_code) \ + printf("ERROR: %s\n", \ + error_messages[error_code]) /**< Print log error message*/ + +#define find_len(arr) sizeof(arr) / sizeof(arr[0]) +static const size_t VEC_MAX = SIZE_MAX / sizeof(int); + +#endif diff --git a/src/char.c b/src/char.c index 4e51096..4080c1e 100644 --- a/src/char.c +++ b/src/char.c @@ -1,64 +1,142 @@ #include "char.h" +#include #include +#include #include #include -/* - * Andrew Haynes - * dmm.dev@icloud.com - * No LICENSE - * Vector Library For C - */ +#include "utils.h" -/** - * Creates a new vector with type char - * @param Takes in nullptr or another vector object. If an object is passed in - * the new vector will have its size incremented by 1 - * @return Returns a new vector object - * - */ - -__attribute__((overloadable)) Vec8_t -create(const Vec8_t* input) +// If -1 for len, returns a blank Vector with no allocated memory +Vec8_t +create(const char* buf, const int len) { - Vec8_t vec = { .arr = nullptr, .size = 0, .capacity = CAPACITY }; - if (input != nullptr && input->size > 0) + Vec8_t dst = { NULL, 0, CAPACITY, VEC_MAX }; + if (len > -1) { - vec.size = input->size + 1; + char* dst_buf = calloc(CAPACITY, sizeof(char)); + dst.arr = dst_buf; } - vec.arr = calloc(vec.capacity, sizeof(char)); - return vec; + if (!dst.arr) + { + LOG("Warning! Buffer not allocated, be careful if this was " + "intentional"); + return dst; + } + if (buf) + { + for (int i = 0; i < len; i++) + { + dst.arr[i] = buf[i]; + dst.size++; + } + } + return dst; } -/** - * Creates a new vector with type char - * @param Takes in a boolean of true or false to determine if a memory - * allocation occurs. True callocs a base memory, false does not - * @return Returns a new vector object - * - */ - -__attribute__((overloadable)) Vec8_t -create(const _Bool init) +Vec8_t +push_back(Vec8_t* vec, const char val) { - Vec8_t vec = { .arr = nullptr, .size = 0, .capacity = CAPACITY }; - if (init) + if (!vec) { - vec.arr = calloc(vec.capacity, sizeof(char)); + LOGERROR(ERR_VECTOR_NULL); + return create(nullptr, -1); } - return vec; + Vec8_t dst = { NULL, vec->size, CAPACITY, vec->max_size }; + + if (!vec->arr) + { + LOGERROR(ERR_BUF_NULL); + return dst; + } + if (vec->size + 1 > vec->max_size) + { + LOGERROR(ERR_MAX_PASSED); + dst = *vec; + return dst; + } + + char* dst_buf; + if (vec->size + 1 > vec->capacity) + { + if (vec->capacity * 2 > vec->max_size) + { + LOGERROR(ERR_MAX_PASSED); + dst = *vec; + return dst; + } + dst.capacity = vec->capacity * 2; + dst_buf = reallocf(vec->arr, dst.capacity * sizeof(char)); + if (!dst_buf) + { + LOGERROR(ERR_ALLOC_FAIL); + return dst; + } + } + else + { + dst_buf = vec->arr; + } + dst.arr = dst_buf; + dst.arr[dst.size] = val; + dst.size++; + return dst; +} + +Vec8_t +pop_back(Vec8_t* vec) +{ + Vec8_t err = create(nullptr, -1); + if (!vec) + { + LOGERROR(ERR_VECTOR_NULL); + return err; + } + if (!vec->arr) + { + LOGERROR(ERR_BUF_NULL); + return err; + } + if (vec->size < 1) + { + LOGERROR(ERR_INVALID_SIZE); + return err; + } + Vec8_t dst = { NULL, vec->size - 1, vec->capacity, vec->max_size }; + dst.arr = vec->arr; + dst.arr[dst.size] = 0; + return dst; } Vec8_t reserve(Vec8_t* ptr, const size_t max_size) { - Vec8_t ret = create(nullptr); - char* res = reallocf(ptr->arr, max_size * sizeof(char)); - ret.arr = res; - ret.capacity = max_size * sizeof(char); - ret.size = ptr->size; - if (ret.size > max_size) ret.size = max_size; + Vec8_t ret = create(nullptr, -1); + if (!ptr) + { + LOGERROR(ERR_VECTOR_NULL); + return ret; + } + if (!ptr->arr) + { + ret.arr = calloc(max_size, sizeof(char)); + } + if (ptr->arr) + { + ret.arr = reallocf(ptr->arr, max_size * sizeof(char)); + ret.size = ptr->size; + if (ret.size > max_size) + { + for (int i = max_size - 1; i > ret.size; i--) + { + ret.arr[i] = 0; + } + ret.size = max_size; + } + } + ret.capacity = max_size; + ret.max_size = max_size; return ret; } @@ -71,7 +149,7 @@ shrink_to_fit(Vec8_t* ptr) int swap(Vec8_t* ptr, Vec8_t* ptr_other) { - Vec8_t empty = create(false); + Vec8_t empty = create(nullptr, 0); if (ptr == nullptr || ptr_other == nullptr) return 0; if (ptr->arr == nullptr || ptr_other->arr == nullptr) return 0; empty.arr = ptr->arr; @@ -103,19 +181,24 @@ data(const Vec8_t* ptr) } size_t -max_size(const Vec8_t* ptr) +capacity(const Vec8_t* ptr) { return ptr->capacity; } +size_t +max_size(const Vec8_t* ptr) +{ + return ptr->max_size; +} + void -delete(Vec8_t* vec) +delete(const Vec8_t* vec) { if (vec->arr != nullptr) { - free(vec->arr); + free((void*)vec->arr); } - vec->arr = nullptr; } Vec8_t @@ -193,12 +276,21 @@ erase(Vec8_t* vec, const size_t iter_start, const size_t iter_end) void print_vec(const Vec8_t* vec) { + if (!vec) + { + LOGERROR(ERR_VECTOR_NULL); + return; + } for (int i = 0; i < vec->size; i++) { if (vec->arr[i]) { printf("%c ", at(vec, i)); } + else + { + LOGERROR(ERR_INVALID_SIZE); + } } printf("\n"); } @@ -249,38 +341,10 @@ empty(const Vec8_t* vec) return 0; } -Vec8_t -add_back(Vec8_t* vec, const char val) -{ - if (vec->size >= vec->capacity) - { - vec->capacity *= 2; - char* nvec = reallocf(vec->arr, vec->capacity * sizeof(char)); - if (nvec == NULL) - { - return *vec; - } - vec->arr = nvec; - } - vec->arr[vec->size] = val; - vec->size++; - return *vec; -} - -Vec8_t -pop_back(Vec8_t* vec) -{ - if (vec == nullptr || vec->arr == nullptr || vec->size <= 0) - return *vec; - vec->arr[vec->size - 1] = 0; - vec->size = vec->size - 1; - return *vec; -} - __attribute__((overloadable)) Vec8_t resize(Vec8_t* vec, size_t size) { - Vec8_t nvec = create(nullptr); + Vec8_t nvec = create(nullptr, 0); if (vec == nullptr || vec->arr == nullptr) return nvec; if (size <= 0 || vec->size <= 0) { @@ -298,7 +362,7 @@ resize(Vec8_t* vec, size_t size) __attribute__((overloadable)) Vec8_t resize(Vec8_t* vec, size_t size, char val) { - Vec8_t nvec = create(nullptr); + Vec8_t nvec = create(nullptr, 0); if (vec == nullptr || vec->arr == nullptr) return nvec; if (size <= 0 || vec->size <= 0) { @@ -338,7 +402,7 @@ resize(Vec8_t* vec, size_t size, char val) __attribute__((overloadable)) Vec8_t assign(Vec8_t* vec, const Vec8_t* iterator, size_t iter_start, size_t iter_end) { - Vec8_t ret = create(nullptr); + Vec8_t ret = create(nullptr, 0); if (vec == nullptr || vec->arr == nullptr) return ret; if (iterator == nullptr || iterator->arr == nullptr) return ret; if (iter_end <= iter_start) return ret; @@ -347,7 +411,7 @@ assign(Vec8_t* vec, const Vec8_t* iterator, size_t iter_start, size_t iter_end) *vec = reserve(vec, res); for (size_t i = iter_start; i < iter_end; i++) { - *vec = add_back(vec, at(iterator, (int)i)); + *vec = push_back(vec, at(iterator, (int)i)); } return *vec; } @@ -355,36 +419,99 @@ assign(Vec8_t* vec, const Vec8_t* iterator, size_t iter_start, size_t iter_end) __attribute__((overloadable)) Vec8_t assign(Vec8_t* vec, const size_t amount, char val) { - Vec8_t ret = create(nullptr); - if (vec == nullptr || vec->arr == nullptr) return ret; + if (vec == nullptr || vec->arr == nullptr) return create(nullptr, 0); vec = erase(vec, begin(vec), end(vec) + 1); *vec = reserve(vec, amount); for (int i = 0; i < amount; i++) { - *vec = add_back(vec, val); + *vec = push_back(vec, val); } return *vec; } +// TODO: Add error checking and null checking +// Follows array style __attribute__((overloadable)) Vec8_t insert(Vec8_t* vec, size_t iter, char val) { + size_t last = vec->size; + *vec = push_back(vec, 0); + for (size_t i = vec->size - 1; i > iter; i--) + { + vec->arr[i] = vec->arr[i - 1]; + } + vec->arr[iter] = val; + + return *vec; } +// TODO: Add error checking and null checking +// Follows array style __attribute__((overloadable)) Vec8_t insert(Vec8_t* vec, size_t iter, size_t amount, char val) { + size_t last = vec->size; + char cpy[vec->size - (iter)]; + size_t cpy_size = (vec->size - (iter)); + int k = 0; + for (size_t i = iter; i < vec->size; i++) + { + cpy[k] = vec->arr[i]; + k++; + } + for (int i = 0; i < amount; i++) + { + *vec = push_back(vec, 0); + } + + if ((iter - 1) + amount <= last) + { + for (int i = iter; i < vec->size; i++) + { + vec->arr[i] = 0; + } + size_t j = iter - 1 + amount; + for (int i = 0; i < cpy_size; i++) + { + vec->arr[j + i] = cpy[i]; + } + for (int i = iter; i < iter + amount - 1; i++) + { + vec->arr[i] = val; + } + } + else + { + return *vec; + } + + return *vec; } +// TODO: Add error checking and null checking +// NOTE: It might be a good idea to move the iter ahead of the src_vec __attribute__((overloadable)) Vec8_t insert(Vec8_t* dst_vec, size_t iter, Vec8_t* src_vec, size_t iter_start, size_t iter_end) { -} + size_t cpy_size = iter_end - iter_start; + char cpy[cpy_size]; + int j = 0; + for (int i = iter_start; i < iter_end; i++) + { + cpy[j] = src_vec->arr[i]; + j++; + } + for (int i = 0; i < cpy_size; i++) + { + printf("%c ", cpy[i]); + } + printf("\n"); + for (int i = 0; i < iter_end - iter_start; i++) + { + insert(dst_vec, (iter_start - 1) + i, cpy[i]); + } + return *dst_vec; -/* insert() Inserts a number of elements into a vector vector can have - vector.insert(iterator position, value); - vector.insert(iterator position, size_t amount, value); - vector.insert(iterator position (vector to add to), iterator to add - with (other vector) iterator start, iterator end); - * */ + // Inserts over an iteration, [0, 5] +} diff --git a/src/main.c b/src/main.c index 2378dbd..25a3f1c 100644 --- a/src/main.c +++ b/src/main.c @@ -14,97 +14,29 @@ #include #include +#include #include "char.h" +#include "utils.h" int main() { - Vec8_t vec = create(nullptr); - Vec8_t other = create(nullptr); - + char arr[] = { 'a' }; + // Vec8_t v1 = create(arr, find_len(arr)); + // Vec8_t v1 = create((char[]) { 'a', 'b', 'c', 'd' }, 4); + Vec8_t v1 = create(nullptr, 0); + // v1 = reserve(&v1, 10); + // v1 = pop_back(&v1); for (int i = 0; i < 10; i++) { - vec = add_back(&vec, 'a'); + v1 = push_back(&v1, 'a'); } - print_vec(&vec); - printf("\n"); - - for (int i = 0; i < 5; i++) - { - other = add_back(&other, 'b'); - } - print_vec(&other); - - printf("Vec: "); - // for (int i = 0; i < vec.size; i++) - // { - // printf("%i ", at(&vec, i)); - // } - print_vec(&vec); - printf("\n"); - - // vec = resize(&vec, 12, 'a'); - - printf("Vec: "); - vec = assign(&vec, &other, begin(&other) + 2, end(&other) + 1); - vec = shrink_to_fit(&vec); - print_vec(&vec); - // for (int i = 0; i < vec.size; i++) - // { - // printf("%i ", at(&vec, i)); - // } - // printf("\n"); - // print_vec(&vec); - // pop_back(&vec); - // printf("Other: "); - // print_vec(&other); - // printf("\n"); - // - // printf("Vec: "); - // print_vec(&vec); - // printf("\n"); - // pop_back(&vec); - // printf("Other: "); - // print_vec(&other); - // printf("\n"); - // - // int error = swap(&vec, &other); - // if (error) - // { - // printf("Vec: "); - // print_vec(&vec); - // printf("\n"); - // printf("Other: "); - // print_vec(&other); - // } - - // Vec8_t vec = create(false); - - // vec = add_back(&vec, '3'); - // vec = add_back(&vec, '4'); - // vec = add_back(&vec, '5'); - // vec = add_back(&vec, '6'); - // vec = add_back(&vec, '8'); - // vec = add_back(&vec, '6'); - - // for (int i = 0; i < vec.capacity; i++) - // { - // printf("%i\n", vec.arr[i]); - // } - // printf("\n"); - // printf("\n"); - // - // vec = shrink_to_fit(&vec); - // for (int i = 0; i < vec.capacity; i++) - // { - // printf("%i\n", vec.arr[i]); - // } - // vec = *erase(&vec, begin(&vec) + 2, begin(&vec) + 4); - // print_vec(&vec); - // printf("%p", data(&vec)); - - delete(&vec); - delete(&other); + print_vec(&v1); + printf("SIZE: %zu\n", v1.size); + v1 = push_back(&v1, 'a'); + print_vec(&v1); + printf("SIZE: %zu\n", v1.size); + delete(&v1); return 0; } diff --git a/src/utils.c b/src/utils.c new file mode 100644 index 0000000..27b6524 --- /dev/null +++ b/src/utils.c @@ -0,0 +1,12 @@ +#include + +const char* error_messages[] = { + [ERR_ALLOC_FAIL] = "Calloc :- Failed to allocate", + [ERR_BUF_NULL] = "Buffer :- NULL", + [ERR_BAD_TYPE] = "Type :- Does not match vector type", + [ERR_INVALID_SIZE] = "Size :- Size is 0 or invalid", + [ERR_VECTOR_NULL] = "Vector :- Given vector is null", + [ERR_MAX_PASSED] = "Max :- Vector Max value is overloaded", + // [ERR_CREATION_FAIL] = "Buffer creation failed", + // [ERR_MALLOC_NULL] = "Malloc Failed to allocate", +};