forked from enlightenment/efl
TES
Conflicts: src/lib/eina/eina_list.c src/lib/eina/eina_types.h
This commit is contained in:
parent
b71a17b9db
commit
d0f3357f77
|
@ -1094,6 +1094,85 @@ eina_list_sort(Eina_List *list, unsigned int limit, Eina_Compare_Cb func)
|
||||||
return list;
|
return list;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
EAPI Eina_List *
|
||||||
|
eina_list_shuffle(Eina_List *list, Eina_Random_Cb func)
|
||||||
|
{
|
||||||
|
unsigned int n, i, j;
|
||||||
|
Eina_List_Accounting *accounting;
|
||||||
|
Eina_List *shuffled_list, *shuffled_last, *li;
|
||||||
|
|
||||||
|
if (!list)
|
||||||
|
return NULL;
|
||||||
|
|
||||||
|
EINA_MAGIC_CHECK_LIST(list, NULL);
|
||||||
|
|
||||||
|
accounting = list->accounting;
|
||||||
|
n = accounting->count;
|
||||||
|
shuffled_list = shuffled_last = NULL;
|
||||||
|
|
||||||
|
if (n == 1)
|
||||||
|
return list;
|
||||||
|
|
||||||
|
while (n > 1)
|
||||||
|
{
|
||||||
|
if (func)
|
||||||
|
i = func(0, (n - 1));
|
||||||
|
else
|
||||||
|
i = (int) ((float)n*rand()/(RAND_MAX+1.0));
|
||||||
|
|
||||||
|
if(i == 0)
|
||||||
|
{
|
||||||
|
li = list;
|
||||||
|
list = list->next;
|
||||||
|
}
|
||||||
|
else if (i == (n - 1) || i == n)
|
||||||
|
{
|
||||||
|
li = accounting->last;
|
||||||
|
accounting->last = li->prev;
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
if (i > (n / 2))
|
||||||
|
for (j = n - 1,
|
||||||
|
li = accounting->last;
|
||||||
|
j!=i;
|
||||||
|
li = li->prev, j--);
|
||||||
|
else
|
||||||
|
for (j = 0,
|
||||||
|
li = list;
|
||||||
|
j!=i;
|
||||||
|
li = li->next, j++);
|
||||||
|
|
||||||
|
li->prev->next = li->next;
|
||||||
|
li->next->prev = li->prev;
|
||||||
|
}
|
||||||
|
|
||||||
|
n--;
|
||||||
|
|
||||||
|
if (shuffled_list == NULL)
|
||||||
|
{
|
||||||
|
li->prev = NULL;
|
||||||
|
shuffled_list = li;
|
||||||
|
shuffled_last = li;
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
shuffled_last->next = li;
|
||||||
|
li->prev = shuffled_last;
|
||||||
|
shuffled_last = li;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
list->next = NULL;
|
||||||
|
list->prev = shuffled_last;
|
||||||
|
shuffled_last->next = list;
|
||||||
|
|
||||||
|
accounting->last = list;
|
||||||
|
shuffled_list->accounting = accounting;
|
||||||
|
|
||||||
|
return shuffled_list;
|
||||||
|
}
|
||||||
|
|
||||||
EAPI Eina_List *
|
EAPI Eina_List *
|
||||||
eina_list_merge(Eina_List *left, Eina_List *right)
|
eina_list_merge(Eina_List *left, Eina_List *right)
|
||||||
{
|
{
|
||||||
|
|
|
@ -333,6 +333,21 @@ typedef int (*Eina_Compare_Cb)(const void *data1, const void *data2);
|
||||||
*/
|
*/
|
||||||
#define EINA_COMPARE_CB(function) ((Eina_Compare_Cb)function)
|
#define EINA_COMPARE_CB(function) ((Eina_Compare_Cb)function)
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @typedef Eina_Random_Cb
|
||||||
|
* Function used in shuffling functions. An integer betwen min and max
|
||||||
|
* inclusive must be returned.
|
||||||
|
*
|
||||||
|
* @since 1.8
|
||||||
|
*/
|
||||||
|
typedef int (*Eina_Random_Cb)(const int min, const int max);
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @def EINA_RANDOM_CB
|
||||||
|
* Macro to cast to Eina_Random_Cb.
|
||||||
|
*/
|
||||||
|
#define EINA_RANDOM_CB(function) ((Eina_Random_Cb)function)
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* @typedef Eina_Each_Cb
|
* @typedef Eina_Each_Cb
|
||||||
* A callback type used when iterating over a container.
|
* A callback type used when iterating over a container.
|
||||||
|
|
|
@ -375,6 +375,62 @@ START_TEST(eina_test_list_split)
|
||||||
}
|
}
|
||||||
END_TEST
|
END_TEST
|
||||||
|
|
||||||
|
static int uicmp(const void *d1, const void *d2)
|
||||||
|
{
|
||||||
|
const unsigned int *a = d1;
|
||||||
|
const unsigned int *b = d2;
|
||||||
|
|
||||||
|
if(*a == *b) return 0;
|
||||||
|
if(*a > *b) return 1;
|
||||||
|
|
||||||
|
return -1;
|
||||||
|
}
|
||||||
|
|
||||||
|
#define SHUFFLE_SZ 100
|
||||||
|
#define SHUFFLE_N 100000
|
||||||
|
START_TEST(eina_test_shuffle)
|
||||||
|
{
|
||||||
|
double d;
|
||||||
|
unsigned int *p;
|
||||||
|
unsigned int i, j;
|
||||||
|
unsigned int n[SHUFFLE_SZ];
|
||||||
|
unsigned int rand_count[SHUFFLE_SZ];
|
||||||
|
Eina_List *list = NULL;
|
||||||
|
Eina_List *item = NULL;
|
||||||
|
|
||||||
|
eina_init();
|
||||||
|
|
||||||
|
for(i = 0; i < SHUFFLE_SZ; i++)
|
||||||
|
{
|
||||||
|
n[i] = i;
|
||||||
|
rand_count[i] = 0;
|
||||||
|
list = eina_list_append(list, &n[i]);
|
||||||
|
}
|
||||||
|
|
||||||
|
for(i = 0; i < SHUFFLE_N; i++)
|
||||||
|
{
|
||||||
|
list = eina_list_shuffle(list, NULL);
|
||||||
|
p = eina_list_nth(list, SHUFFLE_SZ/2);
|
||||||
|
rand_count[*p]++;
|
||||||
|
|
||||||
|
j = 0;
|
||||||
|
list = eina_list_sort(list, 0, (Eina_Compare_Cb)&uicmp);
|
||||||
|
EINA_LIST_FOREACH(list, item, p)
|
||||||
|
fail_if(*p != j++);
|
||||||
|
fail_if(j != SHUFFLE_SZ);
|
||||||
|
}
|
||||||
|
|
||||||
|
d = SHUFFLE_SZ/(float)(SHUFFLE_N);
|
||||||
|
for(i = 0; i < SHUFFLE_SZ; i++)
|
||||||
|
{
|
||||||
|
fail_if(rand_count[i]*d > 1.20f);
|
||||||
|
fail_if(rand_count[i]*d < 0.80f);
|
||||||
|
}
|
||||||
|
|
||||||
|
eina_shutdown();
|
||||||
|
}
|
||||||
|
END_TEST
|
||||||
|
|
||||||
void
|
void
|
||||||
eina_test_list(TCase *tc)
|
eina_test_list(TCase *tc)
|
||||||
{
|
{
|
||||||
|
@ -382,4 +438,5 @@ eina_test_list(TCase *tc)
|
||||||
tcase_add_test(tc, eina_test_merge);
|
tcase_add_test(tc, eina_test_merge);
|
||||||
tcase_add_test(tc, eina_test_sorted_insert);
|
tcase_add_test(tc, eina_test_sorted_insert);
|
||||||
tcase_add_test(tc, eina_test_list_split);
|
tcase_add_test(tc, eina_test_list_split);
|
||||||
|
tcase_add_test(tc, eina_test_shuffle);
|
||||||
}
|
}
|
||||||
|
|
Loading…
Reference in New Issue