moved remove and at functions to headers, improved remove_range functions, added string_strip + string_count, updated tests

AuthorKonata <konata@posteo.jp>
Date
Commit82eaa7a88e583abc59b16d028b7ec9100d1771b2
Parent03135e8
7 files changed, 130 insertions(+), 69 deletions(-)
Minclude/cutils/byte_array.h
@@ -19,14 +19,32 @@ typedef struct Bytearray
1919 Bytearray* bytearray_with_capacity(size_t capacity, size_t element_size);
2020 void delete_bytearray(Bytearray* bytearray, void(*rmv_el) (void*));
2121
22-void* bytearray_at(const Bytearray* bytearray, size_t index);
22+HEDLEY_INLINE
23+static void* bytearray_at(const Bytearray* bytearray, size_t index)
24+{
25+ return bytearray->items+(index*bytearray->element_size);
26+}
2327 #define bytearray_pop(bytearray, retptr) bytearray_pop_at(bytearray, bytearray->length-1, retptr)
2428 void* bytearray_pop_at(Bytearray* bytearray, size_t index, void* retptr);
2529
2630 #define bytearray_push(bytearray, item) bytearray_insert(bytearray, bytearray->length, item)
2731 bool bytearray_insert(Bytearray* bytearray, size_t index, const void* item);
2832
29-void bytearray_remove(Bytearray* bytearray, size_t index, void (*rmv)(void*));
33+HEDLEY_INLINE
34+static void bytearray_remove(Bytearray* bytearray, size_t index, void (*rmv)(void*))
35+{
36+ if(index < bytearray->length)
37+ {
38+ size_t length = bytearray->length;
39+ size_t elsize = bytearray->element_size;
40+ if(rmv)
41+ rmv(&bytearray->items[index*elsize]);
42+
43+ memmove(bytearray->items+index*elsize, bytearray->items+index*elsize+1*elsize, length*elsize-index*elsize-1*elsize);
44+ bytearray->length--;
45+ }
46+}
47+void bytearray_remove_range(Bytearray* bytearray, size_t index, size_t length, void (*rmv)(void*));
3048
3149 bool bytearray_adjust_size(Bytearray* bytearray, size_t size);
3250 bool bytearray_shrink(Bytearray* bytearray);
Minclude/cutils/dyn_string.h
@@ -18,21 +18,36 @@ typedef struct String
1818 String* string_with_capacity(size_t capacity);
1919 void delete_string(String* string);
2020
21-char string_at(const String* string, size_t index);
21+HEDLEY_INLINE
22+static char string_at(const String* string, size_t index)
23+{
24+ return string->chars[index];
25+}
26+
2227 #define string_pop(string) string_pop_at(string, string->length-1)
2328 char string_pop_at(String* string, size_t index);
2429
2530 bool string_insert(String* string, size_t index, char character);
2631 #define string_push(string, character) string_insert(string, string->length, character)
2732
28-void string_remove(String* string, size_t index);
33+HEDLEY_INLINE
34+static void string_remove(String* string, size_t index)
35+{
36+ if(index < string->length)
37+ {
38+ memmove(string->chars+index, string->chars+index+1, (string->length-index-1)*sizeof(*string->chars));
39+ string->length--;
40+ }
41+}
2942 void string_remove_range(String* string, size_t index, size_t length);
43+size_t string_strip(String* string, char character);
3044
3145 bool string_adjust_size(String* string, size_t size);
3246 /* TODO: rework find functions to take extra argument of result count
3347 * and then find that many and return them in a vector/linked list */
3448 bool string_find_char(const String* haystack, const char needle, size_t* pos);
3549 bool string_find_str(const String* haystack, const String* needle, size_t* pos);
50+size_t string_count(const String* string, char character);
3651
3752 bool string_concat(String* string, const String* other);
3853
Minclude/cutils/vector.h
@@ -18,14 +18,28 @@ typedef struct Vector
1818 Vector* vector_with_capacity(size_t capacity);
1919 void delete_vector(Vector* vector, void(*rmv) (void*));
2020
21-void* vector_at(const Vector* vector, size_t index);
21+HEDLEY_INLINE
22+static void* vector_at(const Vector* vector, size_t index)
23+{
24+ return vector->items[index];
25+}
2226 #define vector_pop(vector) vector_pop_at(vector, vector->length-1)
2327 void* vector_pop_at(Vector* vector, size_t index);
2428
2529 bool vector_insert(Vector* vector, size_t index, void* item);
2630 #define vector_push(vector, item) vector_insert(vector, vector->length, item)
2731
28-void vector_remove(Vector* vector, size_t index, void (*rmv)(void*));
32+HEDLEY_INLINE
33+static void vector_remove(Vector* vector, size_t index, void (*rmv)(void*))
34+{
35+ if(index < vector->length)
36+ {
37+ if(rmv)
38+ rmv(vector->items[index]);
39+ memmove(vector->items+index, vector->items+index+1, (vector->length-index-1)*sizeof(*vector->items));
40+ vector->length--;
41+ }
42+}
2943 void vector_remove_range(Vector* vector, size_t index, size_t length, void (*rmv)(void*));
3044
3145 bool vector_adjust_size(Vector* vector, size_t size);
Msrc/byte_array.c
@@ -38,14 +38,21 @@ void delete_bytearray(Bytearray* bytearray, void(*rmv_el) (void*))
3838 free(bytearray);
3939 }
4040
41-void* bytearray_at(const Bytearray* bytearray, size_t index)
41+void bytearray_remove_range(Bytearray* bytearray, size_t index, size_t length, void (*rmv)(void*))
4242 {
43- if(index >= bytearray->length)
44- return NULL;
45- else
46- return bytearray->items+(index*bytearray->element_size);
43+ size_t i;
44+ if(rmv)
45+ {
46+ for(i = index; i < length; i++)
47+ {
48+ rmv(bytearray_at(bytearray, i));
49+ }
50+ }
51+ memmove(bytearray->items+index, bytearray->items+index+length, (bytearray->length-(index+length))*sizeof(*bytearray->items));
52+ bytearray->length -= length;
4753 }
4854
55+
4956 void* bytearray_pop_at(Bytearray* bytearray, size_t index, void* retptr)
5057 {
5158 void *tmp;
@@ -77,20 +84,6 @@ bool bytearray_insert(Bytearray* bytearray, size_t index, const void* item)
7784 return true;
7885 }
7986
80-void bytearray_remove(Bytearray* bytearray, size_t index, void (*rmv)(void*))
81-{
82- if(index < bytearray->length)
83- {
84- size_t length = bytearray->length;
85- size_t elsize = bytearray->element_size;
86- if(rmv)
87- rmv(&bytearray->items[index*elsize]);
88-
89- memmove(bytearray->items+index*elsize, bytearray->items+index*elsize+1*elsize, length*elsize-index*elsize-1*elsize);
90- bytearray->length--;
91- }
92-}
93-
9487 bool bytearray_adjust_size(Bytearray* bytearray, size_t size)
9588 {
9689 while(bytearray->capacity < size)
Msrc/dyn_string.c
@@ -17,22 +17,37 @@ String* string_with_capacity(size_t capacity)
1717 return string;
1818 }
1919
20-void string_remove(String* string, size_t index)
20+void string_remove_range(String* string, size_t index, size_t length)
2121 {
22- if(index < string->length)
23- {
24- memmove(string->chars+index, string->chars+index+1, (string->length-index-1)*sizeof(*string->chars));
25- string->length--;
26- }
22+ memmove(string->chars+index, string->chars+index+length, (string->length-(index+length)));
23+ string->length -= length;
2724 }
28-/* TODO: optimize */
29-void string_remove_range(String* string, size_t index, size_t length)
25+
26+size_t string_strip(String* string, char character)
3027 {
31- size_t i;
32- for(i = 0; i < length; i++)
28+ size_t i, last = 0, offset = 0;
29+ bool first = true;
30+
31+ for(i = 0; i < string->length; i++)
3332 {
34- string_remove(string, index+i);
33+ if(string_at(string,i) == character)
34+ {
35+ if(first)
36+ {
37+ first = false;
38+ } else {
39+ memmove(string->chars+last-offset, string->chars+last+1, i-last-1);
40+ offset++;
41+ }
42+
43+ last = i;
44+ }
3545 }
46+
47+ memmove(string->chars+last-offset, string->chars+last+1, string->length-last-1);
48+
49+ string->length -= offset+(first ? 0 : 1);
50+ return offset;
3651 }
3752
3853 bool string_insert(String* string, size_t index, char character)
@@ -46,14 +61,6 @@ bool string_insert(String* string, size_t index, char character)
4661 return true;
4762 }
4863
49-char string_at(const String* string, size_t index)
50-{
51- if(index >= string->length)
52- return '\0';
53- else
54- return string->chars[index];
55-}
56-
5764 char string_pop_at(String* string, size_t index)
5865 {
5966 char tmp = string_at(string, index);
@@ -110,6 +117,17 @@ bool string_find_str(const String* haystack, const String* needle, size_t* pos)
110117 return false;
111118 }
112119
120+size_t string_count(const String* string, char character)
121+{
122+ size_t i, ret = 0;
123+ for(i = 0; i < string->length; i++)
124+ {
125+ if(string_at(string, i) == character)
126+ ret++;
127+ }
128+ return ret;
129+}
130+
113131 bool string_adjust_size(String* string, size_t size)
114132 {
115133 while(string->capacity < size)
Msrc/test.c
@@ -112,6 +112,19 @@ static void test_string(void)
112112
113113 delete_string(string2);
114114 delete_string(string);
115+
116+ string = from_cstring("abcd");
117+ assert(string->length == 4);
118+ string_remove_range(string, 0, string->length);
119+ assert(string->length == 0);
120+ delete_string(string);
121+
122+ string = from_cstring("bba");
123+ string_strip(string, 'a');
124+ assert(string->length == 2);
125+
126+ cstring = to_cstring_del(string);
127+ free(cstring);
115128 }
116129
117130 static void test_bytearray(void)
@@ -148,14 +161,18 @@ static void test_bytearray(void)
148161 assert(*tmpchar == 'a');
149162 free(tmpchar);
150163
151- tmpchar = bytearray_pop(bt, NULL);
152- assert(tmpchar == NULL);
153-
154164 bytearray_push(bt, "a");
155165 tmpchar = bytearray_pop(bt, NULL);
156166 assert(*tmpchar == 'a');
157167 free(tmpchar);
158168
169+ bytearray_push(bt, "a");
170+ bytearray_push(bt, "a");
171+ bytearray_push(bt, "a");
172+ assert(bt->length == 3);
173+ bytearray_remove_range(bt, 0, bt->length, NULL);
174+ assert(bt->length == 0);
175+
159176 delete_bytearray(bt, NULL);
160177 }
161178 #if __STDC_VERSION__ >= 201112L
@@ -242,6 +259,7 @@ static void test_ll(void)
242259
243260
244261 ll_remove_range(ll, 0, ll->length-1, NULL);
262+ assert(ll->length == 1);
245263
246264 delete_ll(ll, NULL);
247265 }
Msrc/vector.c
@@ -17,14 +17,6 @@ Vector* vector_with_capacity(size_t capacity)
1717 return vector;
1818 }
1919
20-void* vector_at(const Vector* vector, size_t index)
21-{
22- if(index >= vector->length)
23- return NULL;
24- else
25- return vector->items[index];
26-}
27-
2820 void* vector_pop_at(Vector* vector, size_t index)
2921 {
3022 void* tmp = vector_at(vector, index);
@@ -37,25 +29,18 @@ void* vector_pop_at(Vector* vector, size_t index)
3729 }
3830 }
3931
40-
41-void vector_remove(Vector* vector, size_t index, void (*rmv)(void*))
42-{
43- if(index < vector->length)
44- {
45- if(rmv)
46- rmv(vector->items[index]);
47- memmove(vector->items+index, vector->items+index+1, (vector->length-index-1)*sizeof(*vector->items));
48- vector->length--;
49- }
50-}
51-/* TODO: optimize */
5232 void vector_remove_range(Vector* vector, size_t index, size_t length, void (*rmv)(void*))
5333 {
5434 size_t i;
55- for(i = 0; i < length; i++)
35+ if(rmv)
5636 {
57- vector_remove(vector, index+i, rmv);
37+ for(i = index; i < length; i++)
38+ {
39+ rmv(vector_at(vector, i));
40+ }
5841 }
42+ memmove(vector->items+index, vector->items+index+length, (vector->length-(index+length))*sizeof(*vector->items));
43+ vector->length -= length;
5944 }
6045
6146 size_t* vector_find(const Vector* haystack, const void* needle, int (*cmp)(const void*, const void*))