Line data Source code
1 : /*------------------------------------------------------------------------- 2 : * 3 : * qunique.h 4 : * inline array unique functions 5 : * Portions Copyright (c) 2019-2024, PostgreSQL Global Development Group 6 : * 7 : * IDENTIFICATION 8 : * src/include/lib/qunique.h 9 : *------------------------------------------------------------------------- 10 : */ 11 : 12 : #ifndef QUNIQUE_H 13 : #define QUNIQUE_H 14 : 15 : /* 16 : * Remove duplicates from a pre-sorted array, according to a user-supplied 17 : * comparator. Usually the array should have been sorted with qsort() using 18 : * the same arguments. Return the new size. 19 : */ 20 : static inline size_t 21 292808 : qunique(void *array, size_t elements, size_t width, 22 : int (*compare) (const void *, const void *)) 23 : { 24 292808 : char *bytes = (char *) array; 25 : size_t i, 26 : j; 27 : 28 292808 : if (elements <= 1) 29 2114 : return elements; 30 : 31 9800694 : for (i = 1, j = 0; i < elements; ++i) 32 : { 33 9510000 : if (compare(bytes + i * width, bytes + j * width) != 0 && 34 : ++j != i) 35 4972758 : memcpy(bytes + j * width, bytes + i * width, width); 36 : } 37 : 38 290694 : return j + 1; 39 : } 40 : 41 : /* 42 : * Like qunique(), but takes a comparator with an extra user data argument 43 : * which is passed through, for compatibility with qsort_arg(). 44 : */ 45 : static inline size_t 46 4581344 : qunique_arg(void *array, size_t elements, size_t width, 47 : int (*compare) (const void *, const void *, void *), 48 : void *arg) 49 : { 50 4581344 : char *bytes = (char *) array; 51 : size_t i, 52 : j; 53 : 54 4581344 : if (elements <= 1) 55 0 : return elements; 56 : 57 213187282 : for (i = 1, j = 0; i < elements; ++i) 58 : { 59 208605938 : if (compare(bytes + i * width, bytes + j * width, arg) != 0 && 60 : ++j != i) 61 30474726 : memcpy(bytes + j * width, bytes + i * width, width); 62 : } 63 : 64 4581344 : return j + 1; 65 : } 66 : 67 : #endif /* QUNIQUE_H */