CVector  4.1.0
A C++ style vector library in strict ANSI C (C89)
cvector_template2.h
Go to the documentation of this file.
1 #ifndef CVECTOR_TYPE_H
2 #define CVECTOR_TYPE_H
3 
4 #include <stdlib.h>
5 
6 #ifndef CVEC_SIZE_T
7 #define CVEC_SIZE_T size_t
8 #endif
9 
10 #ifndef CVEC_SZ
11 #define CVEC_SZ
13 #endif
14 
15 #ifdef __cplusplus
16 extern "C" {
17 #endif
18 
19 
20 typedef struct cvector_TYPE
21 {
22  TYPE* a;
23  cvec_sz size;
25  void (*elem_free)(void*);
26  int (*elem_init)(void*, void*);
27 } cvector_TYPE;
28 
29 extern cvec_sz CVEC_TYPE_SZ;
30 
31 int cvec_TYPE(cvector_TYPE* vec, cvec_sz size, cvec_sz capacity, void(*elem_free)(void*), int(*elem_init)(void*, void*));
32 int cvec_init_TYPE(cvector_TYPE* vec, TYPE* vals, cvec_sz num, void(*elem_free)(void*), int(*elem_init)(void*, void*));
33 
34 cvector_TYPE* cvec_TYPE_heap(cvec_sz size, cvec_sz capacity, void (*elem_free)(void*), int(*elem_init)(void*, void*));
35 cvector_TYPE* cvec_init_TYPE_heap(TYPE* vals, cvec_sz num, void (*elem_free)(void*), int(*elem_init)(void*, void*));
36 
37 int cvec_copyc_TYPE(void* dest, void* src);
39 
40 int cvec_push_TYPE(cvector_TYPE* vec, TYPE* val);
41 void cvec_pop_TYPE(cvector_TYPE* vec, TYPE* ret);
42 
43 int cvec_pushm_TYPE(cvector_TYPE* vec, TYPE* a);
44 void cvec_popm_TYPE(cvector_TYPE* vec, TYPE* ret);
45 int cvec_insertm_TYPE(cvector_TYPE* vec, cvec_sz i, TYPE* a);
47 void cvec_replacem_TYPE(cvector_TYPE* vec, cvec_sz i, TYPE* a, TYPE* ret);
48 
50 int cvec_insert_TYPE(cvector_TYPE* vec, cvec_sz i, TYPE* a);
52 int cvec_replace_TYPE(cvector_TYPE* vec, cvec_sz i, TYPE* a, TYPE* ret);
57 int cvec_set_val_sz_TYPE(cvector_TYPE* vec, TYPE* val);
58 int cvec_set_val_cap_TYPE(cvector_TYPE* vec, TYPE* val);
59 
61 
63 void cvec_free_TYPE_heap(void* vec);
64 void cvec_free_TYPE(void* vec);
65 
66 #ifdef __cplusplus
67 }
68 #endif
69 
70 /* CVECTOR_TYPE_H */
71 #endif
72 
73 
74 #ifdef CVECTOR_TYPE_IMPLEMENTATION
75 
77 
78 #define CVEC_TYPE_ALLOCATOR(x) ((x+1) * 2)
79 
80 #if defined(CVEC_MALLOC) && defined(CVEC_FREE) && defined(CVEC_REALLOC)
81 /* ok */
82 #elif !defined(CVEC_MALLOC) && !defined(CVEC_FREE) && !defined(CVEC_REALLOC)
83 /* ok */
84 #else
85 #error "Must define all or none of CVEC_MALLOC, CVEC_FREE, and CVEC_REALLOC."
86 #endif
87 
88 #ifndef CVEC_MALLOC
89 #define CVEC_MALLOC(sz) malloc(sz)
90 #define CVEC_REALLOC(p, sz) realloc(p, sz)
91 #define CVEC_FREE(p) free(p)
92 #endif
93 
94 #ifndef CVEC_MEMMOVE
95 #include <string.h>
96 #define CVEC_MEMMOVE(dst, src, sz) memmove(dst, src, sz)
97 #endif
98 
99 #ifndef CVEC_ASSERT
100 #include <assert.h>
101 #define CVEC_ASSERT(x) assert(x)
102 #endif
103 
104 
105 /* general vector */
106 
107 cvector_TYPE* cvec_TYPE_heap(cvec_sz size, cvec_sz capacity, void(*elem_free)(void*), int(*elem_init)(void*, void*))
108 {
109  cvector_TYPE* vec;
110  if (!(vec = (cvector_TYPE*)CVEC_MALLOC(sizeof(cvector_TYPE)))) {
111  CVEC_ASSERT(vec != NULL);
112  return NULL;
113  }
114 
115  vec->size = size;
116  vec->capacity = (capacity > vec->size || (vec->size && capacity == vec->size)) ? capacity : vec->size + CVEC_TYPE_SZ;
117 
118  if (!(vec->a = (TYPE*)CVEC_MALLOC(vec->capacity * sizeof(TYPE)))) {
119  CVEC_ASSERT(vec->a != NULL);
120  CVEC_FREE(vec);
121  return NULL;
122  }
123 
124  vec->elem_free = elem_free;
125  vec->elem_init = elem_init;
126 
127  return vec;
128 }
129 
130 cvector_TYPE* cvec_init_TYPE_heap(TYPE* vals, cvec_sz num, void(*elem_free)(void*), int(*elem_init)(void*, void*))
131 {
132  cvector_TYPE* vec;
133  cvec_sz i;
134 
135  if (!(vec = (cvector_TYPE*)CVEC_MALLOC(sizeof(cvector_TYPE)))) {
136  CVEC_ASSERT(vec != NULL);
137  return NULL;
138  }
139 
140  vec->capacity = num + CVEC_TYPE_SZ;
141  vec->size = num;
142  if (!(vec->a = (TYPE*)CVEC_MALLOC(vec->capacity * sizeof(TYPE)))) {
143  CVEC_ASSERT(vec->a != NULL);
144  CVEC_FREE(vec);
145  return NULL;
146  }
147 
148  if (elem_init) {
149  for (i=0; i<num; ++i) {
150  if (!elem_init(&vec->a[i], &vals[i])) {
151  CVEC_ASSERT(0);
152  CVEC_FREE(vec->a);
153  CVEC_FREE(vec);
154  return NULL;
155  }
156  }
157  } else {
158  CVEC_MEMMOVE(vec->a, vals, sizeof(TYPE)*num);
159  }
160 
161  vec->elem_free = elem_free;
162  vec->elem_init = elem_init;
163 
164  return vec;
165 }
166 
167 int cvec_TYPE(cvector_TYPE* vec, cvec_sz size, cvec_sz capacity, void(*elem_free)(void*), int(*elem_init)(void*, void*))
168 {
169  vec->size = size;
170  vec->capacity = (capacity > vec->size || (vec->size && capacity == vec->size)) ? capacity : vec->size + CVEC_TYPE_SZ;
171 
172  if (!(vec->a = (TYPE*)CVEC_MALLOC(vec->capacity * sizeof(TYPE)))) {
173  CVEC_ASSERT(vec->a != NULL);
174  vec->size = vec->capacity = 0;
175  return 0;
176  }
177 
178  vec->elem_free = elem_free;
179  vec->elem_init = elem_init;
180 
181  return 1;
182 }
183 
184 int cvec_init_TYPE(cvector_TYPE* vec, TYPE* vals, cvec_sz num, void(*elem_free)(void*), int(*elem_init)(void*, void*))
185 {
186  cvec_sz i;
187 
188  vec->capacity = num + CVEC_TYPE_SZ;
189  vec->size = num;
190  if (!(vec->a = (TYPE*)CVEC_MALLOC(vec->capacity * sizeof(TYPE)))) {
191  CVEC_ASSERT(vec->a != NULL);
192  vec->size = vec->capacity = 0;
193  return 0;
194  }
195 
196  if (elem_init) {
197  for (i=0; i<num; ++i) {
198  if (!elem_init(&vec->a[i], &vals[i])) {
199  CVEC_ASSERT(0);
200  return 0;
201  }
202  }
203  } else {
204  CVEC_MEMMOVE(vec->a, vals, sizeof(TYPE)*num);
205  }
206 
207  vec->elem_free = elem_free;
208  vec->elem_init = elem_init;
209 
210  return 1;
211 }
212 
213 int cvec_copyc_TYPE(void* dest, void* src)
214 {
215  cvector_TYPE* vec1 = (cvector_TYPE*)dest;
216  cvector_TYPE* vec2 = (cvector_TYPE*)src;
217 
218  vec1->a = NULL;
219  vec1->size = 0;
220  vec1->capacity = 0;
221 
222  return cvec_copy_TYPE(vec1, vec2);
223 }
224 
226 {
227  int i;
228  TYPE* tmp = NULL;
229  if (!(tmp = (TYPE*)CVEC_REALLOC(dest->a, src->capacity*sizeof(TYPE)))) {
230  CVEC_ASSERT(tmp != NULL);
231  return 0;
232  }
233  dest->a = tmp;
234 
235  if (src->elem_init) {
236  for (i=0; i<src->size; ++i) {
237  if (!src->elem_init(&dest->a[i], &src->a[i])) {
238  CVEC_ASSERT(0);
239  return 0;
240  }
241  }
242  } else {
243  /* could use memcpy here since we know we just allocated dest->a */
244  CVEC_MEMMOVE(dest->a, src->a, src->size*sizeof(TYPE));
245  }
246 
247  dest->size = src->size;
248  dest->capacity = src->capacity;
249  dest->elem_free = src->elem_free;
250  dest->elem_init = src->elem_init;
251  return 1;
252 }
253 
254 int cvec_push_TYPE(cvector_TYPE* vec, TYPE* a)
255 {
256  TYPE* tmp;
257  cvec_sz tmp_sz;
258  if (vec->capacity == vec->size) {
259  tmp_sz = CVEC_TYPE_ALLOCATOR(vec->capacity);
260  if (!(tmp = (TYPE*)CVEC_REALLOC(vec->a, sizeof(TYPE)*tmp_sz))) {
261  CVEC_ASSERT(tmp != NULL);
262  return 0;
263  }
264  vec->a = tmp;
265  vec->capacity = tmp_sz;
266  }
267  if (vec->elem_init) {
268  if (!vec->elem_init(&vec->a[vec->size], a)) {
269  CVEC_ASSERT(0);
270  return 0;
271  }
272  } else {
273  CVEC_MEMMOVE(&vec->a[vec->size], a, sizeof(TYPE));
274  }
275 
276  vec->size++;
277  return 1;
278 }
279 
280 int cvec_pushm_TYPE(cvector_TYPE* vec, TYPE* a)
281 {
282  TYPE* tmp;
283  cvec_sz tmp_sz;
284  if (vec->capacity == vec->size) {
285  tmp_sz = CVEC_TYPE_ALLOCATOR(vec->capacity);
286  if (!(tmp = (TYPE*)CVEC_REALLOC(vec->a, sizeof(TYPE)*tmp_sz))) {
287  CVEC_ASSERT(tmp != NULL);
288  return 0;
289  }
290  vec->a = tmp;
291  vec->capacity = tmp_sz;
292  }
293  CVEC_MEMMOVE(&vec->a[vec->size], a, sizeof(TYPE));
294 
295  vec->size++;
296  return 1;
297 }
298 
299 void cvec_pop_TYPE(cvector_TYPE* vec, TYPE* ret)
300 {
301  vec->size--;
302  if (ret) {
303  CVEC_MEMMOVE(ret, &vec->a[vec->size], sizeof(TYPE));
304  }
305 
306  if (vec->elem_free) {
307  vec->elem_free(&vec->a[vec->size]);
308  }
309 }
310 
311 void cvec_popm_TYPE(cvector_TYPE* vec, TYPE* ret)
312 {
313  vec->size--;
314  if (ret) {
315  CVEC_MEMMOVE(ret, &vec->a[vec->size], sizeof(TYPE));
316  }
317 }
318 
320 TYPE* cvec_back_TYPE(cvector_TYPE* vec)
321 {
322  return &vec->a[vec->size-1];
323 }
324 
326 {
327  TYPE* tmp;
328  cvec_sz tmp_sz;
329  if (vec->capacity < vec->size + num) {
330  tmp_sz = vec->capacity + num + CVEC_TYPE_SZ;
331  if (!(tmp = (TYPE*)CVEC_REALLOC(vec->a, sizeof(TYPE)*tmp_sz))) {
332  CVEC_ASSERT(tmp != NULL);
333  return 0;
334  }
335  vec->a = tmp;
336  vec->capacity = tmp_sz;
337  }
338 
339  vec->size += num;
340  return 1;
341 }
342 
343 int cvec_insert_TYPE(cvector_TYPE* vec, cvec_sz i, TYPE* a)
344 {
345  TYPE* tmp;
346  cvec_sz tmp_sz;
347  if (vec->capacity == vec->size) {
348  tmp_sz = CVEC_TYPE_ALLOCATOR(vec->capacity);
349  if (!(tmp = (TYPE*)CVEC_REALLOC(vec->a, sizeof(TYPE)*tmp_sz))) {
350  CVEC_ASSERT(tmp != NULL);
351  return 0;
352  }
353 
354  vec->a = tmp;
355  vec->capacity = tmp_sz;
356  }
357  CVEC_MEMMOVE(&vec->a[i+1], &vec->a[i], (vec->size-i)*sizeof(TYPE));
358 
359  if (vec->elem_init) {
360  if (!vec->elem_init(&vec->a[i], a)) {
361  CVEC_ASSERT(0);
362  return 0;
363  }
364  } else {
365  CVEC_MEMMOVE(&vec->a[i], a, sizeof(TYPE));
366  }
367 
368  vec->size++;
369  return 1;
370 }
371 
372 int cvec_insertm_TYPE(cvector_TYPE* vec, cvec_sz i, TYPE* a)
373 {
374  TYPE* tmp;
375  cvec_sz tmp_sz;
376  if (vec->capacity == vec->size) {
377  tmp_sz = CVEC_TYPE_ALLOCATOR(vec->capacity);
378  if (!(tmp = (TYPE*)CVEC_REALLOC(vec->a, sizeof(TYPE)*tmp_sz))) {
379  CVEC_ASSERT(tmp != NULL);
380  return 0;
381  }
382 
383  vec->a = tmp;
384  vec->capacity = tmp_sz;
385  }
386  CVEC_MEMMOVE(&vec->a[i+1], &vec->a[i], (vec->size-i)*sizeof(TYPE));
387 
388  CVEC_MEMMOVE(&vec->a[i], a, sizeof(TYPE));
389 
390  vec->size++;
391  return 1;
392 }
393 
394 int cvec_insert_array_TYPE(cvector_TYPE* vec, cvec_sz i, TYPE* a, cvec_sz num)
395 {
396  TYPE* tmp;
397  cvec_sz tmp_sz, j;
398  if (vec->capacity < vec->size + num) {
399  tmp_sz = vec->capacity + num + CVEC_TYPE_SZ;
400  if (!(tmp = (TYPE*)CVEC_REALLOC(vec->a, sizeof(TYPE)*tmp_sz))) {
401  CVEC_ASSERT(tmp != NULL);
402  return 0;
403  }
404  vec->a = tmp;
405  vec->capacity = tmp_sz;
406  }
407 
408  CVEC_MEMMOVE(&vec->a[i+num], &vec->a[i], (vec->size-i)*sizeof(TYPE));
409  if (vec->elem_init) {
410  for (j=0; j<num; ++j) {
411  if (!vec->elem_init(&vec->a[j+i], &a[j])) {
412  CVEC_ASSERT(0);
413  return 0;
414  }
415  }
416  } else {
417  CVEC_MEMMOVE(&vec->a[i], a, num*sizeof(TYPE));
418  }
419  vec->size += num;
420  return 1;
421 }
422 
423 int cvec_insert_arraym_TYPE(cvector_TYPE* vec, cvec_sz i, TYPE* a, cvec_sz num)
424 {
425  TYPE* tmp;
426  cvec_sz tmp_sz;
427  if (vec->capacity < vec->size + num) {
428  tmp_sz = vec->capacity + num + CVEC_VOID_START_SZ;
429  if (!(tmp = (TYPE*)CVEC_REALLOC(vec->a, sizeof(TYPE)*tmp_sz))) {
430  CVEC_ASSERT(tmp != NULL);
431  return 0;
432  }
433  vec->a = tmp;
434  vec->capacity = tmp_sz;
435  }
436 
437  CVEC_MEMMOVE(&vec->a[i+num], &vec->a[i], (vec->size-i)*sizeof(TYPE));
438 
439  CVEC_MEMMOVE(&vec->a[i], a, num*sizeof(TYPE));
440  vec->size += num;
441  return 1;
442 }
443 
444 int cvec_replace_TYPE(cvector_TYPE* vec, cvec_sz i, TYPE* a, TYPE* ret)
445 {
446  if (ret) {
447  CVEC_MEMMOVE(ret, &vec->a[i], sizeof(TYPE));
448  } else if (vec->elem_free) {
449  vec->elem_free(&vec->a[i]);
450  }
451 
452  if (vec->elem_init) {
453  if (!vec->elem_init(&vec->a[i], a)) {
454  CVEC_ASSERT(0);
455  return 0;
456  }
457  } else {
458  CVEC_MEMMOVE(&vec->a[i], a, sizeof(TYPE));
459  }
460  return 1;
461 }
462 
463 void cvec_replacem_TYPE(cvector_TYPE* vec, cvec_sz i, TYPE* a, TYPE* ret)
464 {
465  if (ret) {
466  CVEC_MEMMOVE(ret, &vec->a[i], sizeof(TYPE));
467  }
468 
469  CVEC_MEMMOVE(&vec->a[i], a, sizeof(TYPE));
470 }
471 
472 void cvec_erase_TYPE(cvector_TYPE* vec, cvec_sz start, cvec_sz end)
473 {
474  cvec_sz i;
475  cvec_sz d = end - start + 1;
476  if (vec->elem_free) {
477  for (i=start; i<=end; i++) {
478  vec->elem_free(&vec->a[i]);
479  }
480  }
481  CVEC_MEMMOVE(&vec->a[start], &vec->a[end+1], (vec->size-1-end)*sizeof(TYPE));
482  vec->size -= d;
483 }
484 
485 void cvec_remove_TYPE(cvector_TYPE* vec, cvec_sz start, cvec_sz end)
486 {
487  cvec_sz d = end - start + 1;
488  CVEC_MEMMOVE(&vec->a[start], &vec->a[end+1], (vec->size-1-end)*sizeof(TYPE));
489  vec->size -= d;
490 }
491 
492 int cvec_reserve_TYPE(cvector_TYPE* vec, cvec_sz size)
493 {
494  TYPE* tmp;
495  if (vec->capacity < size) {
496  if (!(tmp = (TYPE*)CVEC_REALLOC(vec->a, sizeof(TYPE)*(size+CVEC_TYPE_SZ)))) {
497  CVEC_ASSERT(tmp != NULL);
498  return 0;
499  }
500  vec->a = tmp;
501  vec->capacity = size + CVEC_TYPE_SZ;
502  }
503  return 1;
504 }
505 
506 int cvec_set_cap_TYPE(cvector_TYPE* vec, cvec_sz size)
507 {
508  cvec_sz i;
509  TYPE* tmp;
510  if (size < vec->size) {
511  if (vec->elem_free) {
512  for (i=vec->size-1; i>=size; i--) {
513  vec->elem_free(&vec->a[i]);
514  }
515  }
516  vec->size = size;
517  }
518 
519  vec->capacity = size;
520 
521  if (!(tmp = (TYPE*)CVEC_REALLOC(vec->a, sizeof(TYPE)*size))) {
522  CVEC_ASSERT(tmp != NULL);
523  return 0;
524  }
525  vec-> a = tmp;
526  return 1;
527 }
528 
529 int cvec_set_val_sz_TYPE(cvector_TYPE* vec, TYPE* val)
530 {
531  cvec_sz i;
532 
533  if (vec->elem_free) {
534  for(i=0; i<vec->size; i++) {
535  vec->elem_free(&vec->a[i]);
536  }
537  }
538 
539  if (vec->elem_init) {
540  for (i=0; i<vec->size; i++) {
541  if (!vec->elem_init(&vec->a[i], val)) {
542  CVEC_ASSERT(0);
543  return 0;
544  }
545  }
546  } else {
547  for (i=0; i<vec->size; i++) {
548  CVEC_MEMMOVE(&vec->a[i], val, sizeof(TYPE));
549  }
550  }
551  return 1;
552 }
553 
554 int cvec_set_val_cap_TYPE(cvector_TYPE* vec, TYPE* val)
555 {
556  cvec_sz i;
557  if (vec->elem_free) {
558  for (i=0; i<vec->size; i++) {
559  vec->elem_free(&vec->a[i]);
560  }
561  vec->size = vec->capacity;
562  }
563 
564  if (vec->elem_init) {
565  for (i=0; i<vec->capacity; i++) {
566  if (!vec->elem_init(&vec->a[i], val)) {
567  CVEC_ASSERT(0);
568  return 0;
569  }
570  }
571  } else {
572  for (i=0; i<vec->capacity; i++) {
573  CVEC_MEMMOVE(&vec->a[i], val, sizeof(TYPE));
574  }
575  }
576  return 1;
577 }
578 
579 void cvec_clear_TYPE(cvector_TYPE* vec)
580 {
581  cvec_sz i;
582  if (vec->elem_free) {
583  for (i=0; i<vec->size; ++i) {
584  vec->elem_free(&vec->a[i]);
585  }
586  }
587  vec->size = 0;
588 }
589 
590 void cvec_free_TYPE_heap(void* vec)
591 {
592  cvec_sz i;
593  cvector_TYPE* tmp = (cvector_TYPE*)vec;
594  if (!tmp) return;
595  if (tmp->elem_free) {
596  for (i=0; i<tmp->size; i++) {
597  tmp->elem_free(&tmp->a[i]);
598  }
599  }
600  CVEC_FREE(tmp->a);
601  CVEC_FREE(tmp);
602 }
603 
604 void cvec_free_TYPE(void* vec)
605 {
606  cvec_sz i;
607  cvector_TYPE* tmp = (cvector_TYPE*)vec;
608  if (tmp->elem_free) {
609  for (i=0; i<tmp->size; i++) {
610  tmp->elem_free(&tmp->a[i]);
611  }
612  }
613 
614  CVEC_FREE(tmp->a);
615 
616  tmp->size = 0;
617  tmp->capacity = 0;
618 }
619 
620 
621 #endif
#define CVEC_FREE(p)
Definition: cvector.h:71
#define CVEC_REALLOC(p, sz)
Definition: cvector.h:70
#define CVEC_MEMMOVE(dst, src, sz)
Definition: cvector.h:76
#define CVEC_MALLOC(sz)
Definition: cvector.h:69
#define CVEC_ASSERT(x)
Definition: cvector.h:81
CVEC_SIZE_T cvec_sz
Definition: cvector.h:88
cvec_sz CVEC_VOID_START_SZ
Definition: cvector_void.c:29
int cvec_set_cap_TYPE(cvector_TYPE *vec, cvec_sz size)
int cvec_reserve_TYPE(cvector_TYPE *vec, cvec_sz size)
TYPE * cvec_back_TYPE(cvector_TYPE *vec)
int cvec_copy_TYPE(cvector_TYPE *dest, cvector_TYPE *src)
int cvec_set_val_cap_TYPE(cvector_TYPE *vec, TYPE *val)
void cvec_erase_TYPE(cvector_TYPE *vec, cvec_sz start, cvec_sz end)
int cvec_insertm_TYPE(cvector_TYPE *vec, cvec_sz i, TYPE *a)
int cvec_insert_TYPE(cvector_TYPE *vec, cvec_sz i, TYPE *a)
void cvec_free_TYPE(void *vec)
void cvec_popm_TYPE(cvector_TYPE *vec, TYPE *ret)
int cvec_pushm_TYPE(cvector_TYPE *vec, TYPE *a)
int cvec_push_TYPE(cvector_TYPE *vec, TYPE *val)
void cvec_pop_TYPE(cvector_TYPE *vec, TYPE *ret)
int cvec_set_val_sz_TYPE(cvector_TYPE *vec, TYPE *val)
cvector_TYPE * cvec_init_TYPE_heap(TYPE *vals, cvec_sz num, void(*elem_free)(void *), int(*elem_init)(void *, void *))
int cvec_init_TYPE(cvector_TYPE *vec, TYPE *vals, cvec_sz num, void(*elem_free)(void *), int(*elem_init)(void *, void *))
cvector_TYPE * cvec_TYPE_heap(cvec_sz size, cvec_sz capacity, void(*elem_free)(void *), int(*elem_init)(void *, void *))
int cvec_insert_arraym_TYPE(cvector_TYPE *vec, cvec_sz i, TYPE *a, cvec_sz num)
void cvec_replacem_TYPE(cvector_TYPE *vec, cvec_sz i, TYPE *a, TYPE *ret)
int cvec_replace_TYPE(cvector_TYPE *vec, cvec_sz i, TYPE *a, TYPE *ret)
void cvec_free_TYPE_heap(void *vec)
int cvec_TYPE(cvector_TYPE *vec, cvec_sz size, cvec_sz capacity, void(*elem_free)(void *), int(*elem_init)(void *, void *))
CVEC_SIZE_T cvec_sz
void cvec_clear_TYPE(cvector_TYPE *vec)
int cvec_insert_array_TYPE(cvector_TYPE *vec, cvec_sz i, TYPE *a, cvec_sz num)
int cvec_copyc_TYPE(void *dest, void *src)
#define CVEC_SIZE_T
cvec_sz CVEC_TYPE_SZ
void cvec_remove_TYPE(cvector_TYPE *vec, cvec_sz start, cvec_sz end)
int cvec_extend_TYPE(cvector_TYPE *vec, cvec_sz num)
Data structure for TYPE vector.
TYPE * a
Array.
int(* elem_init)(void *, void *)
cvec_sz size
Current size (amount you use when manipulating array directly).
void(* elem_free)(void *)
cvec_sz capacity
Allocated size of array; always >= size.