src/array_list.c

changeset 623
21082350a590
parent 622
3d93cd78aa20
child 624
b0bdff7d8203
equal deleted inserted replaced
622:3d93cd78aa20 623:21082350a590
99 99
100 /* return successfully */ 100 /* return successfully */
101 return CX_ARRAY_COPY_SUCCESS; 101 return CX_ARRAY_COPY_SUCCESS;
102 } 102 }
103 103
104 #define CX_ARRAY_SWAP_SBO_SIZE 512
105
106 void cx_array_swap(
107 void *arr,
108 size_t elem_size,
109 size_t idx1,
110 size_t idx2
111 ) {
112 /* short circuit */
113 if (idx1 == idx2) return;
114
115 char sbo_mem[CX_ARRAY_SWAP_SBO_SIZE];
116 void *tmp;
117
118 /* decide if we can use the local buffer */
119 if (elem_size > CX_ARRAY_SWAP_SBO_SIZE) {
120 tmp = malloc(elem_size);
121 /* we don't want to enforce error handling */
122 if (tmp == NULL) abort();
123 } else {
124 tmp = sbo_mem;
125 }
126
127 /* calculate memory locations */
128 char *left = arr, *right = arr;
129 left += idx1 * elem_size;
130 right += idx2 * elem_size;
131
132 /* three-way swap */
133 memcpy(tmp, left, elem_size);
134 memcpy(left, right, elem_size);
135 memcpy(right, tmp, elem_size);
136
137 /* free dynamic memory, if it was needed */
138 if (tmp != sbo_mem) {
139 free(tmp);
140 }
141 }
142
104 /* HIGH LEVEL ARRAY LIST FUNCTIONS */ 143 /* HIGH LEVEL ARRAY LIST FUNCTIONS */
105 144
106 typedef struct { 145 typedef struct {
107 struct cx_list_s base; 146 struct cx_list_s base;
108 void *data; 147 void *data;
288 return list->size < other->size ? -1 : 1; 327 return list->size < other->size ? -1 : 1;
289 } 328 }
290 } 329 }
291 330
292 static void cx_arl_reverse(struct cx_list_s *list) { 331 static void cx_arl_reverse(struct cx_list_s *list) {
293 332 if (list->size < 2) return;
333 void *data = ((cx_array_list const *) list)->data;
334 size_t half = list->size / 2;
335 for (size_t i = 0; i < half; i++) {
336 cx_array_swap(data, list->itemsize, i, list->size - 1 - i);
337 }
294 } 338 }
295 339
296 static bool cx_arl_iter_valid(struct cx_iterator_s const *iter) { 340 static bool cx_arl_iter_valid(struct cx_iterator_s const *iter) {
297 struct cx_list_s const *list = iter->src_handle; 341 struct cx_list_s const *list = iter->src_handle;
298 return iter->index < list->size; 342 return iter->index < list->size;

mercurial