1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38 #ifndef UCX_ARRAY_LIST_H
39 #define UCX_ARRAY_LIST_H
40
41 #include "list.h"
42
43 #ifdef __cplusplus
44 extern "C" {
45 #endif
46
47
48
49
50 extern unsigned cx_array_swap_sbo_size;
51
52
53
54
55
56
57
58
59
60
61 #define CX_ARRAY_DECLARE(type, name) \
62 type * name; \
63 size_t name##_size; \
64 size_t name##_capacity
65
66
67
68
69
70
71
72
73 #define cx_array_initialize(array, capacity) \
74 array##_capacity = capacity; \
75 array##_size =
0; \
76 array = malloc(
sizeof(array[
0]) * capacity)
77
78
79
80
81 struct cx_array_reallocator_s {
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97 void *(*realloc)(
98 void *array,
99 size_t capacity,
100 size_t elem_size,
101 struct cx_array_reallocator_s *alloc
102 );
103
104
105
106
107 void *ptr1;
108
109
110
111 void *ptr2;
112
113
114
115 size_t int1;
116
117
118
119 size_t int2;
120 };
121
122
123
124
125 extern struct cx_array_reallocator_s *cx_array_default_reallocator;
126
127
128
129
130 enum cx_array_result {
131 CX_ARRAY_SUCCESS,
132 CX_ARRAY_REALLOC_NOT_SUPPORTED,
133 CX_ARRAY_REALLOC_FAILED,
134 };
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162 __attribute__((__nonnull__(
1,
2,
5)))
163 enum cx_array_result cx_array_copy(
164 void **target,
165 size_t *size,
166 size_t *capacity,
167 size_t index,
168 const void *src,
169 size_t elem_size,
170 size_t elem_count,
171 struct cx_array_reallocator_s *reallocator
172 );
173
174
175
176
177
178
179
180
181
182
183 #define cx_array_simple_copy(array, index, src, count) \
184 cx_array_copy((
void**)&(array), &(array##_size), &(array##_capacity), \
185 index, src,
sizeof((array)[
0]), count, cx_array_default_reallocator)
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206 #define cx_array_add(target, size, capacity, elem_size, elem, reallocator) \
207 cx_array_copy((
void**)(target), size, capacity, *(size), elem, elem_size,
1, reallocator)
208
209
210
211
212
213
214
215
216
217 #define cx_array_simple_add(array, elem) \
218 cx_array_simple_copy(array, array##_size, &(elem),
1)
219
220
221
222
223
224
225
226
227
228
229
230
231
232
233
234
235
236
237
238
239
240 __attribute__((__nonnull__))
241 enum cx_array_result cx_array_insert_sorted(
242 void **target,
243 size_t *size,
244 size_t *capacity,
245 cx_compare_func cmp_func,
246 const void *src,
247 size_t elem_size,
248 size_t elem_count,
249 struct cx_array_reallocator_s *reallocator
250 );
251
252
253
254
255
256
257
258
259
260
261
262
263
264
265
266
267
268
269 #define cx_array_add_sorted(target, size, capacity, elem_size, elem, cmp_func, reallocator) \
270 cx_array_insert_sorted((
void**)(target), size, capacity, cmp_func, elem, elem_size,
1, reallocator)
271
272
273
274
275
276
277
278
279
280
281 #define cx_array_simple_add_sorted(array, elem, cmp_func) \
282 cx_array_add_sorted(&array, &(array##_size), &(array##_capacity), \
283 sizeof((array)[
0]), &(elem), cmp_func, cx_array_default_reallocator)
284
285
286
287
288
289
290
291
292
293
294
295 #define cx_array_simple_insert_sorted(array, src, n, cmp_func) \
296 cx_array_insert_sorted((
void**)(&array), &(array##_size), &(array##_capacity), \
297 cmp_func, src,
sizeof((array)[
0]), n, cx_array_default_reallocator)
298
299
300
301
302
303
304
305
306
307
308
309
310
311
312
313
314
315
316
317
318
319
320 __attribute__((__nonnull__))
321 size_t cx_array_binary_search_inf(
322 const void *arr,
323 size_t size,
324 size_t elem_size,
325 const void *elem,
326 cx_compare_func cmp_func
327 );
328
329
330
331
332
333
334
335
336
337
338
339
340
341
342
343 __attribute__((__nonnull__))
344 static inline
size_t cx_array_binary_search(
345 const void *arr,
346 size_t size,
347 size_t elem_size,
348 const void *elem,
349 cx_compare_func cmp_func
350 ) {
351 size_t index = cx_array_binary_search_inf(
352 arr, size, elem_size, elem, cmp_func
353 );
354 if (index < size && cmp_func(((
const char *) arr) + index * elem_size, elem) ==
0) {
355 return index;
356 }
else {
357 return size;
358 }
359 }
360
361
362
363
364
365
366
367
368
369
370
371
372
373
374
375
376
377
378
379
380
381 __attribute__((__nonnull__))
382 static inline
size_t cx_array_binary_search_sup(
383 const void *arr,
384 size_t size,
385 size_t elem_size,
386 const void *elem,
387 cx_compare_func cmp_func
388 ) {
389 size_t inf = cx_array_binary_search_inf(arr, size, elem_size, elem, cmp_func);
390 if (inf == size) {
391
392 return 0;
393 }
else if (cmp_func(((
const char *) arr) + inf * elem_size, elem) ==
0) {
394 return inf;
395 }
else {
396 return inf +
1;
397 }
398 }
399
400
401
402
403
404
405
406
407
408 __attribute__((__nonnull__))
409 void cx_array_swap(
410 void *arr,
411 size_t elem_size,
412 size_t idx1,
413 size_t idx2
414 );
415
416
417
418
419
420
421
422
423
424
425
426
427
428
429
430
431
432 CxList *cxArrayListCreate(
433 const CxAllocator *allocator,
434 cx_compare_func comparator,
435 size_t elem_size,
436 size_t initial_capacity
437 );
438
439
440
441
442
443
444
445
446
447
448
449
450
451
452
453
454 #define cxArrayListCreateSimple(elem_size, initial_capacity) \
455 cxArrayListCreate(
NULL,
NULL, elem_size, initial_capacity)
456
457 #ifdef __cplusplus
458 }
459 #endif
460
461 #endif
462