/** * Vector implementation. * * - Implement each of the functions to create a working growable array (vector). * - Do not change any of the structs * - When submitting, You should not have any 'printf' statements in your vector * functions. * * IMPORTANT: The initial capacity and the vector's growth factor should be * expressed in terms of the configuration constants in vect.h */ #include <assert.h> #include <stdlib.h> #include <string.h> #include "vect.h" /** Main data structure for the vector. */ struct vect { char **data; /* Array containing the actual data. */ unsigned int size; /* Number of items currently in the vector. */ unsigned int capacity; /* Maximum number of items the vector can hold before growing. */ }; /** Construct a new empty vector. */ vect_t *vect_new() { vect_t *v = malloc(sizeof(vect_t)); v->data = malloc(sizeof(char*) * VECT_INITIAL_CAPACITY); v->capacity = VECT_INITIAL_CAPACITY; v->size = 0; return v; } /** Delete the vector, freeing all memory it occupies. */ void vect_delete(vect_t *v) { assert(v!= NULL); // assumption: vector shouldn't be null for (int i = 0; i < v->size; i++) { free(v->data[i]); } free(v->data); free(v); } /** Get the element at the given index. */ const char *vect_get(vect_t *v, unsigned int idx) { assert(v != NULL); assert(idx < v->size); return v->data[idx]; } /** Get a copy of the element at the given index. The caller is responsible * for freeing the memory occupied by the copy. */ char *vect_get_copy(vect_t *v, unsigned int idx) { assert(v != NULL); assert(idx < v->size); int nsize = strlen(v->data[idx]) + 1; char *v_copy = malloc(nsize); strncpy(v_copy, v->data[idx], nsize); return v_copy; } /** Set the element at the given index. */ void vect_set(vect_t *v, unsigned int idx, const char *elt) { assert(v != NULL); assert(idx < v->size); int nsize = strlen(elt) + 1; free(v->data[idx]); v->data[idx] = malloc(nsize); strncpy(v->data[idx], elt, nsize); } /** Add an element to the back of the vector. */ void vect_add(vect_t *v, const char *elt) { assert(v != NULL); // now, use growth factor if adding goes over capacity if (v->size >= v->capacity) { v->capacity = (v->capacity * VECT_GROWTH_FACTOR); v->data = realloc(v->data, sizeof(char*) * v->capacity); } // allocate more space int nsize = strlen(elt) + 1; v->data[v->size] = malloc(nsize); strncpy(v->data[v->size], elt, nsize); v->size = v->size + 1; } /** Remove the last element from the vector. */ void vect_remove_last(vect_t *v) { assert(v != NULL); // free it and then change size free(v->data[v->size - 1]); v->size = v->size - 1; } /** The number of items currently in the vector. */ unsigned int vect_size(vect_t *v) { assert(v != NULL); return v->size; } /** The maximum number of items the vector can hold before it has to grow. */ unsigned int vect_current_capacity(vect_t *v) { assert(v != NULL); return v->capacity; }