integrate priority queue: lumiera namespace prefix; unit test pass
This commit is contained in:
parent
fc3cc1bc98
commit
7f68bc9020
6 changed files with 98 additions and 466 deletions
|
|
@ -31,12 +31,12 @@
|
|||
|
||||
|
||||
|
||||
PriQueue
|
||||
priqueue_init (PriQueue self,
|
||||
LumieraPriQueue
|
||||
lumiera_priqueue_init (LumieraPriQueue self,
|
||||
size_t element_size,
|
||||
priqueue_cmp_fn cmpfn,
|
||||
priqueue_copy_fn copyfn,
|
||||
priqueue_resize_fn resizefn)
|
||||
lumiera_priqueue_cmp_fn cmpfn,
|
||||
lumiera_priqueue_copy_fn copyfn,
|
||||
lumiera_priqueue_resize_fn resizefn)
|
||||
{
|
||||
TRACE (priqueue, "%p", self);
|
||||
|
||||
|
|
@ -55,7 +55,7 @@ priqueue_init (PriQueue self,
|
|||
self->copyfn = copyfn;
|
||||
|
||||
if (!resizefn)
|
||||
resizefn = priqueue_clib_resize;
|
||||
resizefn = lumiera_priqueue_clib_resize;
|
||||
self->resizefn = resizefn;
|
||||
|
||||
self = self->resizefn (self);
|
||||
|
|
@ -65,8 +65,8 @@ priqueue_init (PriQueue self,
|
|||
|
||||
|
||||
|
||||
PriQueue
|
||||
priqueue_destroy (PriQueue self)
|
||||
LumieraPriQueue
|
||||
lumiera_priqueue_destroy (LumieraPriQueue self)
|
||||
{
|
||||
TRACE (priqueue, "%p", self);
|
||||
if (self)
|
||||
|
|
@ -80,8 +80,8 @@ priqueue_destroy (PriQueue self)
|
|||
|
||||
|
||||
|
||||
PriQueue
|
||||
priqueue_reserve (PriQueue self, unsigned elements)
|
||||
LumieraPriQueue
|
||||
lumiera_priqueue_reserve (LumieraPriQueue self, unsigned elements)
|
||||
{
|
||||
TRACE (priqueue, "%p %d", self, elements);
|
||||
if (self)
|
||||
|
|
@ -105,8 +105,8 @@ priqueue_reserve (PriQueue self, unsigned elements)
|
|||
|
||||
|
||||
|
||||
PriQueue
|
||||
priqueue_clib_resize (PriQueue self)
|
||||
LumieraPriQueue
|
||||
lumiera_priqueue_clib_resize (LumieraPriQueue self)
|
||||
{
|
||||
if (self)
|
||||
{
|
||||
|
|
@ -168,14 +168,14 @@ priqueue_clib_resize (PriQueue self)
|
|||
|
||||
|
||||
static inline void*
|
||||
pq_index (PriQueue self, unsigned nth)
|
||||
pq_index (LumieraPriQueue self, unsigned nth)
|
||||
{
|
||||
return (char*)self->queue+self->element_size*nth;
|
||||
}
|
||||
|
||||
|
||||
static inline void
|
||||
pq_up (PriQueue self, void* tmp)
|
||||
pq_up (LumieraPriQueue self, void* tmp)
|
||||
{
|
||||
unsigned i = self->used;
|
||||
unsigned p = i/2;
|
||||
|
|
@ -191,8 +191,8 @@ pq_up (PriQueue self, void* tmp)
|
|||
|
||||
|
||||
|
||||
PriQueue
|
||||
priqueue_insert (PriQueue self, void* element)
|
||||
LumieraPriQueue
|
||||
lumiera_priqueue_insert (LumieraPriQueue self, void* element)
|
||||
{
|
||||
TRACE (priqueue, "%p: insert %p", self, element);
|
||||
|
||||
|
|
@ -211,7 +211,7 @@ priqueue_insert (PriQueue self, void* element)
|
|||
|
||||
|
||||
static inline void
|
||||
pq_down (PriQueue self, void* tmp)
|
||||
pq_down (LumieraPriQueue self, void* tmp)
|
||||
{
|
||||
if (!self->used)
|
||||
return;
|
||||
|
|
@ -234,8 +234,8 @@ pq_down (PriQueue self, void* tmp)
|
|||
}
|
||||
|
||||
|
||||
PriQueue
|
||||
priqueue_remove (PriQueue self)
|
||||
LumieraPriQueue
|
||||
lumiera_priqueue_remove (LumieraPriQueue self)
|
||||
{
|
||||
TRACE (priqueue, "%p: remove", self);
|
||||
|
||||
|
|
@ -253,138 +253,3 @@ priqueue_remove (PriQueue self)
|
|||
|
||||
return self;
|
||||
}
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
#ifdef PRIQUEUE_TEST /* testing */
|
||||
|
||||
#include <stdio.h>
|
||||
|
||||
|
||||
void
|
||||
nobug_priqueue_invariant (PriQueue self, int depth, const struct nobug_context invariant_context, void* extra)
|
||||
{
|
||||
intptr_t n = 1+(intptr_t)extra;
|
||||
|
||||
intptr_t m=n+n;
|
||||
|
||||
if (self && depth && m <= self->used)
|
||||
{
|
||||
INVARIANT_ASSERT (self->cmpfn (pq_index(self, n-1), pq_index(self, m-1)) <= 0, "%d %d", (int)n-1, (int)m-2);
|
||||
nobug_priqueue_invariant (self, depth-1, invariant_context, (void*)m-1);
|
||||
|
||||
if (m<self->used)
|
||||
{
|
||||
INVARIANT_ASSERT (self->cmpfn (pq_index(self, n-1), pq_index(self, m)) <= 0, "%d %d", (int)n-1, (int)m-1);
|
||||
nobug_priqueue_invariant (self, depth-1, invariant_context, (void*)m);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
static int
|
||||
cmpintptr (void* a, void* b)
|
||||
{
|
||||
return *(int*)a - *(int*)b;
|
||||
}
|
||||
|
||||
NOBUG_DEFINE_FLAG (priqueue_test);
|
||||
|
||||
int main()
|
||||
{
|
||||
NOBUG_INIT;
|
||||
NOBUG_INIT_FLAG (priqueue_test);
|
||||
|
||||
priqueue pq;
|
||||
|
||||
PriQueue r;
|
||||
|
||||
int data;
|
||||
|
||||
r = priqueue_init (&pq,
|
||||
sizeof (int),
|
||||
cmpintptr,
|
||||
NULL,
|
||||
NULL);
|
||||
ENSURE (r==&pq);
|
||||
|
||||
#if 1
|
||||
data = 10;
|
||||
r = priqueue_insert (&pq, &data);
|
||||
ENSURE (r==&pq);
|
||||
TRACE (priqueue_test, "inserted %d", data);
|
||||
#endif
|
||||
|
||||
#if 0
|
||||
data = 5;
|
||||
r = priqueue_insert (&pq, &data);
|
||||
ENSURE (r==&pq);
|
||||
TRACE (priqueue_test, "inserted %d", data);
|
||||
#endif
|
||||
|
||||
|
||||
#if 0
|
||||
data = 15;
|
||||
r = priqueue_insert (&pq, &data);
|
||||
ENSURE (r==&pq);
|
||||
TRACE (priqueue_test, "inserted %d", data);
|
||||
|
||||
data = 20;
|
||||
r = priqueue_insert (&pq, &data);
|
||||
ENSURE (r==&pq);
|
||||
TRACE (priqueue_test, "inserted %d", data);
|
||||
#endif
|
||||
|
||||
|
||||
|
||||
|
||||
#if 1
|
||||
for (int i = 0; i < 1000000; ++i)
|
||||
{
|
||||
data = i;
|
||||
r = priqueue_insert (&pq, &data);
|
||||
ENSURE (r==&pq);
|
||||
TRACE (priqueue_test, "inserted %d", data);
|
||||
}
|
||||
|
||||
#endif
|
||||
|
||||
#if 1
|
||||
for (int i = 0; i < 1000000; ++i)
|
||||
{
|
||||
data = rand()%1000000;
|
||||
r = priqueue_insert (&pq, &data);
|
||||
ENSURE (r==&pq);
|
||||
TRACE (priqueue_test, "inserted %d", data);
|
||||
}
|
||||
#endif
|
||||
|
||||
NOBUG_INVARIANT(priqueue, &pq, 100, NULL);
|
||||
|
||||
|
||||
#if 1
|
||||
for (int i = 0; pq.used; ++i)
|
||||
{
|
||||
TRACE (priqueue_test, "TOP: %d", *(int*)priqueue_peek (&pq));
|
||||
r = priqueue_remove (&pq);
|
||||
ENSURE (r==&pq);
|
||||
}
|
||||
#endif
|
||||
|
||||
|
||||
r = priqueue_destroy (&pq);
|
||||
ENSURE (r==&pq);
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
|
||||
|
||||
|
||||
#endif
|
||||
|
|
|
|||
|
|
@ -47,22 +47,22 @@
|
|||
#include "lib/error.h"
|
||||
|
||||
|
||||
typedef struct priqueue_struct priqueue;
|
||||
typedef priqueue* PriQueue;
|
||||
typedef struct lumiera_priqueue_struct lumiera_priqueue;
|
||||
typedef lumiera_priqueue* LumieraPriQueue;
|
||||
|
||||
/** function to compare 2 keys, mandatory */
|
||||
typedef int (*priqueue_cmp_fn)(void*, void*);
|
||||
typedef int (*lumiera_priqueue_cmp_fn)(void*, void*);
|
||||
|
||||
/** function to copy elements, optional.
|
||||
* Has the same prototype as memcpy which is used by default */
|
||||
typedef void *(*priqueue_copy_fn)(void *dest, const void *src, size_t n);
|
||||
typedef void *(*lumiera_priqueue_copy_fn)(void *dest, const void *src, size_t n);
|
||||
|
||||
/** called when used hits the high or low water marks and initially by priqueue_init() (with queue==NULL)
|
||||
* or at priqueue_destroy (with queue != NULL, used elements == 0), optional.
|
||||
*
|
||||
* @note must be aware of resizes by more than just incrementing the queue by one
|
||||
*/
|
||||
typedef PriQueue (*priqueue_resize_fn) (PriQueue);
|
||||
typedef LumieraPriQueue (*lumiera_priqueue_resize_fn) (LumieraPriQueue);
|
||||
|
||||
|
||||
/**
|
||||
|
|
@ -71,7 +71,7 @@ typedef PriQueue (*priqueue_resize_fn) (PriQueue);
|
|||
* which has to reallocate the queue and update
|
||||
* the high and low water marks.
|
||||
*/
|
||||
struct priqueue_struct
|
||||
struct lumiera_priqueue_struct
|
||||
{
|
||||
void* queue;
|
||||
size_t element_size;
|
||||
|
|
@ -79,10 +79,10 @@ struct priqueue_struct
|
|||
unsigned high_water; ///< elements in the queue
|
||||
unsigned low_water; ///< size for shrinking the queue
|
||||
|
||||
priqueue_cmp_fn cmpfn;
|
||||
priqueue_copy_fn copyfn;
|
||||
lumiera_priqueue_cmp_fn cmpfn;
|
||||
lumiera_priqueue_copy_fn copyfn;
|
||||
|
||||
priqueue_resize_fn resizefn;
|
||||
lumiera_priqueue_resize_fn resizefn;
|
||||
};
|
||||
|
||||
|
||||
|
|
@ -90,17 +90,17 @@ struct priqueue_struct
|
|||
|
||||
|
||||
|
||||
PriQueue
|
||||
priqueue_init (PriQueue self,
|
||||
LumieraPriQueue
|
||||
lumiera_priqueue_init (LumieraPriQueue self,
|
||||
size_t element_size,
|
||||
priqueue_cmp_fn cmpfn,
|
||||
priqueue_copy_fn copyfn,
|
||||
priqueue_resize_fn resizefn);
|
||||
lumiera_priqueue_cmp_fn cmpfn,
|
||||
lumiera_priqueue_copy_fn copyfn,
|
||||
lumiera_priqueue_resize_fn resizefn);
|
||||
|
||||
|
||||
|
||||
PriQueue
|
||||
priqueue_destroy (PriQueue self);
|
||||
LumieraPriQueue
|
||||
lumiera_priqueue_destroy (LumieraPriQueue self);
|
||||
|
||||
|
||||
/**
|
||||
|
|
@ -108,8 +108,8 @@ priqueue_destroy (PriQueue self);
|
|||
* and then sets low_water to 0, disabling shrinking
|
||||
* @note on overflow resize will re-enable low_water if it is not aware of this
|
||||
*/
|
||||
PriQueue
|
||||
priqueue_reserve (PriQueue self, unsigned elements);
|
||||
LumieraPriQueue
|
||||
lumiera_priqueue_reserve (LumieraPriQueue self, unsigned elements);
|
||||
|
||||
|
||||
/**
|
||||
|
|
@ -118,8 +118,8 @@ priqueue_reserve (PriQueue self, unsigned elements);
|
|||
* doubles this when the high water mark is hit,
|
||||
* shrinks at high_water/8-8 (that is, 64 is the minimum size)
|
||||
*/
|
||||
PriQueue
|
||||
priqueue_clib_resize (PriQueue self);
|
||||
LumieraPriQueue
|
||||
lumiera_priqueue_clib_resize (LumieraPriQueue self);
|
||||
|
||||
|
||||
|
||||
|
|
@ -129,8 +129,8 @@ priqueue_clib_resize (PriQueue self);
|
|||
* the element will be copied
|
||||
* @return \c NULL on error
|
||||
*/
|
||||
PriQueue
|
||||
priqueue_insert (PriQueue self, void* element);
|
||||
LumieraPriQueue
|
||||
lumiera_priqueue_insert (LumieraPriQueue self, void* element);
|
||||
|
||||
|
||||
/**
|
||||
|
|
@ -139,7 +139,7 @@ priqueue_insert (PriQueue self, void* element);
|
|||
* as no insert or remove is called
|
||||
*/
|
||||
static inline void*
|
||||
priqueue_peek (PriQueue self)
|
||||
lumiera_priqueue_peek (LumieraPriQueue self)
|
||||
{
|
||||
if (self && self->queue)
|
||||
return self->queue;
|
||||
|
|
@ -152,8 +152,8 @@ priqueue_peek (PriQueue self)
|
|||
* removes the topmost element
|
||||
* @return \c NULL on error (empty queue, resize failure)
|
||||
*/
|
||||
PriQueue
|
||||
priqueue_remove (PriQueue self);
|
||||
LumieraPriQueue
|
||||
lumiera_priqueue_remove (LumieraPriQueue self);
|
||||
|
||||
|
||||
|
||||
|
|
|
|||
|
|
@ -38,14 +38,13 @@
|
|||
#include <string.h>
|
||||
#include <nobug.h>
|
||||
|
||||
NOBUG_DEFINE_FLAG_LIMIT(TEST, LOG_DEBUG);
|
||||
|
||||
|
||||
#define TESTS_BEGIN \
|
||||
int \
|
||||
main (int argc, const char** argv) \
|
||||
{ \
|
||||
NOBUG_INIT; \
|
||||
NOBUG_INIT_FLAG (TEST); \
|
||||
unsigned testcnt=0; \
|
||||
int ret = 0; \
|
||||
\
|
||||
|
|
|
|||
6
tests/15priqueue.tests
Normal file
6
tests/15priqueue.tests
Normal file
|
|
@ -0,0 +1,6 @@
|
|||
TESTING "Priority Queue" ./test-priqueue
|
||||
|
||||
TEST "fill and clear" <<END
|
||||
return: 0
|
||||
END
|
||||
|
||||
|
|
@ -40,7 +40,7 @@ return: 0
|
|||
END
|
||||
|
||||
TEST "C++ plugin test" plugin_exampleplugin_cpp <<END
|
||||
out: opened 0x.+ global interfaces 0x...
|
||||
out: opened \S+ global interfaces \S+
|
||||
out: Hallo Welt!
|
||||
out: Tschüss schnöde Welt!
|
||||
out: Hello World!
|
||||
|
|
|
|||
|
|
@ -1,5 +1,5 @@
|
|||
/*
|
||||
PriQueue - simple heap based priority queue
|
||||
TEST_PRIQUEUE - test the heap based priority queue implementation
|
||||
|
||||
Copyright (C) Lumiera.org
|
||||
2011, Christian Thaeter <ct@pipapo.org>
|
||||
|
|
@ -21,254 +21,22 @@
|
|||
* *****************************************************/
|
||||
|
||||
|
||||
#include "lib/test/test.h"
|
||||
#include "lib/priqueue.h"
|
||||
#include "include/logging.h"
|
||||
|
||||
#include <stdint.h>
|
||||
#include <nobug.h>
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
PriQueue
|
||||
priqueue_init (PriQueue self,
|
||||
size_t element_size,
|
||||
priqueue_cmp_fn cmpfn,
|
||||
priqueue_copy_fn copyfn,
|
||||
priqueue_resize_fn resizefn)
|
||||
{
|
||||
TRACE (priqueue, "%p", self);
|
||||
|
||||
REQUIRE (element_size);
|
||||
REQUIRE (cmpfn);
|
||||
|
||||
if (self)
|
||||
{
|
||||
self->queue = NULL;
|
||||
self->element_size = element_size;
|
||||
self->used = self->high_water = self->low_water = 0;
|
||||
self->cmpfn = cmpfn;
|
||||
|
||||
if (!copyfn)
|
||||
copyfn = memcpy;
|
||||
self->copyfn = copyfn;
|
||||
|
||||
if (!resizefn)
|
||||
resizefn = priqueue_clib_resize;
|
||||
self->resizefn = resizefn;
|
||||
|
||||
self = self->resizefn (self);
|
||||
}
|
||||
return self;
|
||||
}
|
||||
|
||||
|
||||
|
||||
PriQueue
|
||||
priqueue_destroy (PriQueue self)
|
||||
{
|
||||
TRACE (priqueue, "%p", self);
|
||||
if (self)
|
||||
{
|
||||
WARN_IF (self->used, priqueue, "queue was not empty");
|
||||
self->used = 0;
|
||||
self = self->resizefn (self);
|
||||
}
|
||||
return self;
|
||||
}
|
||||
|
||||
|
||||
|
||||
PriQueue
|
||||
priqueue_reserve (PriQueue self, unsigned elements)
|
||||
{
|
||||
TRACE (priqueue, "%p %d", self, elements);
|
||||
if (self)
|
||||
{
|
||||
if (self->used+elements >= self->high_water)
|
||||
{
|
||||
self->used += elements;
|
||||
self = self->resizefn (self);
|
||||
if (!self)
|
||||
{
|
||||
ERROR (priqueue, "resize failed");
|
||||
return NULL;
|
||||
}
|
||||
self->used -= elements;
|
||||
}
|
||||
self->low_water = 0;
|
||||
}
|
||||
|
||||
return self;
|
||||
}
|
||||
|
||||
|
||||
|
||||
PriQueue
|
||||
priqueue_clib_resize (PriQueue self)
|
||||
{
|
||||
if (self)
|
||||
{
|
||||
if (!self->queue)
|
||||
{
|
||||
INFO (priqueue, "%p: initial alloc", self);
|
||||
self->queue = malloc (64*self->element_size);
|
||||
ERROR_IF (!self->queue, priqueue, "%p: allocation failed", self);
|
||||
if (!self->queue)
|
||||
return NULL;
|
||||
self->high_water = 64;
|
||||
}
|
||||
else
|
||||
{
|
||||
if (self->used)
|
||||
{
|
||||
if (self->used >= self->high_water)
|
||||
{
|
||||
unsigned newwater = self->high_water;
|
||||
while (self->used >= newwater)
|
||||
newwater *= 2;
|
||||
|
||||
INFO (priqueue, "%p: resize %d -> %d", self, self->high_water, newwater);
|
||||
|
||||
void* newqueue = realloc (self->queue, self->element_size * newwater);
|
||||
ERROR_IF (!newqueue, priqueue, "%p: allocation failed", self);
|
||||
if (!newqueue)
|
||||
return NULL;
|
||||
self->queue = newqueue;
|
||||
self->high_water = newwater;
|
||||
self->low_water = self->high_water/8-8;
|
||||
TRACE (priqueue, "%p: low_water: %d", self, self->low_water);
|
||||
}
|
||||
else
|
||||
{
|
||||
INFO (priqueue, "%p: shrink %d -> %d", self, self->high_water, (self->low_water+8)*4);
|
||||
void* newqueue = realloc (self->queue, self->element_size * (self->low_water+8)*4);
|
||||
|
||||
ERROR_IF (!newqueue, priqueue, "allocation failed");
|
||||
if (!newqueue)
|
||||
return NULL;
|
||||
self->queue = newqueue;
|
||||
self->high_water = (self->low_water+8)*4;
|
||||
self->low_water = self->high_water/8-8;
|
||||
TRACE (priqueue, "%p: low_water: %d", self, self->low_water);
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
INFO (priqueue, "%p: freeing", self);
|
||||
free (self->queue);
|
||||
self->queue = NULL;
|
||||
}
|
||||
}
|
||||
}
|
||||
return self;
|
||||
}
|
||||
|
||||
|
||||
|
||||
/* @note internal helper copied from priqueue.c */
|
||||
static inline void*
|
||||
pq_index (PriQueue self, unsigned nth)
|
||||
pq_index (LumieraPriQueue self, unsigned nth)
|
||||
{
|
||||
return (char*)self->queue+self->element_size*nth;
|
||||
}
|
||||
|
||||
|
||||
static inline void
|
||||
pq_up (PriQueue self, void* tmp)
|
||||
{
|
||||
unsigned i = self->used;
|
||||
unsigned p = i/2;
|
||||
|
||||
while (p && self->cmpfn (tmp, pq_index(self, p-1)) < 0)
|
||||
{
|
||||
self->copyfn (pq_index (self, i-1), pq_index (self, p-1), self->element_size);
|
||||
i=p; p=i/2;
|
||||
}
|
||||
|
||||
self->copyfn (pq_index (self, i-1), tmp, self->element_size);
|
||||
}
|
||||
|
||||
|
||||
|
||||
PriQueue
|
||||
priqueue_insert (PriQueue self, void* element)
|
||||
{
|
||||
TRACE (priqueue, "%p: insert %p", self, element);
|
||||
|
||||
if (self && self->used >= self->high_water)
|
||||
self = self->resizefn (self);
|
||||
|
||||
if (self)
|
||||
{
|
||||
++self->used;
|
||||
pq_up (self, element);
|
||||
}
|
||||
return self;
|
||||
}
|
||||
|
||||
|
||||
|
||||
|
||||
static inline void
|
||||
pq_down (PriQueue self, void* tmp)
|
||||
{
|
||||
if (!self->used)
|
||||
return;
|
||||
|
||||
unsigned i = 1;
|
||||
|
||||
while (i <= self->used/2)
|
||||
{
|
||||
unsigned n=i+i;
|
||||
if (n<self->used && self->cmpfn (pq_index(self, n-1), pq_index(self, n)) >= 0)
|
||||
++n;
|
||||
|
||||
if (self->cmpfn (tmp, pq_index(self, n-1)) < 0)
|
||||
break;
|
||||
|
||||
self->copyfn (pq_index (self, i-1), pq_index (self, n-1), self->element_size);
|
||||
i = n;
|
||||
}
|
||||
self->copyfn (pq_index (self, i-1), tmp, self->element_size);
|
||||
}
|
||||
|
||||
|
||||
PriQueue
|
||||
priqueue_remove (PriQueue self)
|
||||
{
|
||||
TRACE (priqueue, "%p: remove", self);
|
||||
|
||||
if (self)
|
||||
{
|
||||
if (!self->used)
|
||||
return NULL;
|
||||
|
||||
--self->used;
|
||||
pq_down (self, pq_index (self, self->used));
|
||||
|
||||
if (self->used < self->low_water)
|
||||
self = self->resizefn (self);
|
||||
}
|
||||
|
||||
return self;
|
||||
}
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
#ifdef PRIQUEUE_TEST /* testing */
|
||||
|
||||
#include <stdio.h>
|
||||
|
||||
|
||||
void
|
||||
nobug_priqueue_invariant (PriQueue self, int depth, const struct nobug_context invariant_context, void* extra)
|
||||
nobug_priqueue_invariant (LumieraPriQueue self, int depth, const struct nobug_context invariant_context, void* extra)
|
||||
{
|
||||
intptr_t n = 1+(intptr_t)extra;
|
||||
|
||||
|
|
@ -294,97 +62,91 @@ cmpintptr (void* a, void* b)
|
|||
return *(int*)a - *(int*)b;
|
||||
}
|
||||
|
||||
NOBUG_DEFINE_FLAG (priqueue_test);
|
||||
|
||||
int main()
|
||||
{
|
||||
NOBUG_INIT;
|
||||
NOBUG_INIT_FLAG (priqueue_test);
|
||||
|
||||
priqueue pq;
|
||||
|
||||
PriQueue r;
|
||||
|
||||
int data;
|
||||
|
||||
r = priqueue_init (&pq,
|
||||
|
||||
|
||||
|
||||
TESTS_BEGIN
|
||||
|
||||
lumiera_priqueue pq;
|
||||
|
||||
LumieraPriQueue r;
|
||||
|
||||
int data, prev, curr;
|
||||
|
||||
r = lumiera_priqueue_init (&pq,
|
||||
sizeof (int),
|
||||
cmpintptr,
|
||||
NULL,
|
||||
NULL);
|
||||
ENSURE (r==&pq);
|
||||
|
||||
#if 1
|
||||
|
||||
data = 10;
|
||||
r = priqueue_insert (&pq, &data);
|
||||
r = lumiera_priqueue_insert (&pq, &data);
|
||||
ENSURE (r==&pq);
|
||||
TRACE (priqueue_test, "inserted %d", data);
|
||||
#endif
|
||||
TRACE (test, "inserted %d", data);
|
||||
|
||||
|
||||
#if 0
|
||||
data = 5;
|
||||
r = priqueue_insert (&pq, &data);
|
||||
r = lumiera_priqueue_insert (&pq, &data);
|
||||
ENSURE (r==&pq);
|
||||
TRACE (priqueue_test, "inserted %d", data);
|
||||
#endif
|
||||
TRACE (test, "inserted %d", data);
|
||||
|
||||
|
||||
#if 0
|
||||
data = 15;
|
||||
r = priqueue_insert (&pq, &data);
|
||||
r = lumiera_priqueue_insert (&pq, &data);
|
||||
ENSURE (r==&pq);
|
||||
TRACE (priqueue_test, "inserted %d", data);
|
||||
TRACE (test, "inserted %d", data);
|
||||
|
||||
data = 20;
|
||||
r = priqueue_insert (&pq, &data);
|
||||
r = lumiera_priqueue_insert (&pq, &data);
|
||||
ENSURE (r==&pq);
|
||||
TRACE (priqueue_test, "inserted %d", data);
|
||||
#endif
|
||||
TRACE (test, "inserted %d", data);
|
||||
|
||||
|
||||
|
||||
|
||||
#if 1
|
||||
for (int i = 0; i < 1000000; ++i)
|
||||
{
|
||||
data = i;
|
||||
r = priqueue_insert (&pq, &data);
|
||||
r = lumiera_priqueue_insert (&pq, &data);
|
||||
ENSURE (r==&pq);
|
||||
TRACE (priqueue_test, "inserted %d", data);
|
||||
TRACE (test, "inserted %d", data);
|
||||
}
|
||||
|
||||
#endif
|
||||
|
||||
#if 1
|
||||
for (int i = 0; i < 1000000; ++i)
|
||||
{
|
||||
data = rand()%1000000;
|
||||
r = priqueue_insert (&pq, &data);
|
||||
r = lumiera_priqueue_insert (&pq, &data);
|
||||
ENSURE (r==&pq);
|
||||
TRACE (priqueue_test, "inserted %d", data);
|
||||
TRACE (test, "inserted %d", data);
|
||||
}
|
||||
#endif
|
||||
|
||||
NOBUG_INVARIANT(priqueue, &pq, 100, NULL);
|
||||
|
||||
|
||||
#if 1
|
||||
prev = 0;
|
||||
for (int i = 0; pq.used; ++i)
|
||||
{
|
||||
TRACE (priqueue_test, "TOP: %d", *(int*)priqueue_peek (&pq));
|
||||
r = priqueue_remove (&pq);
|
||||
curr = *(int*)lumiera_priqueue_peek (&pq);
|
||||
TRACE (test, "TOP: %d", curr);
|
||||
CHECK (prev <= curr, "priority ordering broken");
|
||||
prev = curr;
|
||||
|
||||
r = lumiera_priqueue_remove (&pq);
|
||||
ENSURE (r==&pq);
|
||||
}
|
||||
#endif
|
||||
|
||||
|
||||
r = priqueue_destroy (&pq);
|
||||
r = lumiera_priqueue_destroy (&pq);
|
||||
ENSURE (r==&pq);
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
|
||||
|
||||
|
||||
#endif
|
||||
TESTS_END
|
||||
|
|
|
|||
Loading…
Reference in a new issue