Annotation of embedaddon/bird2/lib/heap_test.c, revision 1.1.1.1
1.1 misho 1: /*
2: * BIRD Library -- Universal Heap Macros Tests
3: *
4: * (c) 2015 CZ.NIC z.s.p.o.
5: *
6: * Can be freely distributed and used under the terms of the GNU GPL.
7: */
8:
9: #include "test/birdtest.h"
10: #include "sysdep/config.h"
11: #include "lib/heap.h"
12:
13: #define MAX_NUM 1000
14: #define SPECIAL_KEY -3213
15:
16: #define MY_CMP(x, y) ((x) < (y))
17:
18: #define MY_HEAP_SWAP(heap,a,b,t) \
19: do { \
20: bt_debug("swap(%u %u) ", a, b); \
21: HEAP_SWAP(heap,a,b,t); \
22: } while(0)
23:
24: static int heap[MAX_NUM+1];
25: static uint num;
26:
27: /*
28: * A valid heap must follow these rules:
29: * - `num >= 0`
30: * - `heap[i] >= heap[i / 2]` for each `i` in `[2, num]`
31: */
32: static int
33: is_heap_valid(int heap[], uint num)
34: {
35: uint i;
36:
37: if (num > MAX_NUM)
38: return 0;
39:
40: for (i = 2; i <= num; i++)
41: if (heap[i] < heap[i / 2])
42: return 0;
43:
44: return 1;
45: }
46:
47: static void
48: show_heap(void)
49: {
50: uint i;
51: bt_debug("\n");
52: bt_debug("numbers %u; ", num);
53: for (i = 0; i <= num; i++)
54: bt_debug("%d ", heap[i]);
55: bt_debug(is_heap_valid(heap, num) ? "OK" : "NON-VALID HEAP!");
56: bt_debug("\n");
57: }
58:
59: static void
60: init_heap(void)
61: {
62: uint i;
63: num = 0;
64: heap[0] = SPECIAL_KEY; /* heap[0] should be unused */
65: for (i = 1; i <= MAX_NUM; i++)
66: heap[i] = 0;
67: }
68:
69: static int
70: t_heap_insert(void)
71: {
72: uint i;
73:
74: init_heap();
75:
76: for (i = MAX_NUM; i >= 1; i--)
77: {
78: bt_debug("ins %u at pos %u ", i, MAX_NUM - i);
79: heap[MAX_NUM - i + 1] = i;
80: HEAP_INSERT(heap, ++num, int, MY_CMP, MY_HEAP_SWAP);
81: show_heap();
82: bt_assert(is_heap_valid(heap, num));
83: }
84:
85: return 1;
86: }
87:
88: static int
89: t_heap_increase_decrease(void)
90: {
91: uint i;
92:
93: t_heap_insert();
94:
95: for (i = 1; i <= MAX_NUM; i++)
96: {
97: if ((int)i > heap[i])
98: {
99: bt_debug("inc %u ", i);
100: heap[i] = i;
101: HEAP_INCREASE(heap, num, int, MY_CMP, MY_HEAP_SWAP, i);
102: }
103: else if ((int)i < heap[i])
104: {
105: bt_debug("dec %u ", i);
106: heap[i] = i;
107: HEAP_INCREASE(heap, num, int, MY_CMP, MY_HEAP_SWAP, i);
108: }
109: show_heap();
110: bt_assert(is_heap_valid(heap, num));
111: }
112:
113: return 1;
114: }
115:
116: static int
117: t_heap_delete(void)
118: {
119: uint i;
120:
121: t_heap_insert();
122:
123: for (i = 1; i <= num; i++)
124: {
125: bt_debug("del at pos %u ", i);
126: HEAP_DELETE(heap, num, int, MY_CMP, MY_HEAP_SWAP, i);
127: show_heap();
128: bt_assert(is_heap_valid(heap, num));
129: }
130:
131: return 1;
132: }
133:
134: static int
135: t_heap_0(void)
136: {
137: init_heap();
138: t_heap_insert();
139: t_heap_increase_decrease();
140: t_heap_delete();
141:
142: return heap[0] == SPECIAL_KEY;
143: }
144:
145: static int
146: t_heap_insert_random(void)
147: {
148: int i, j;
149: int expected[MAX_NUM+1];
150:
151: init_heap();
152:
153: for (i = 1; i <= MAX_NUM; i++)
154: {
155: heap[i] = expected[i] = bt_random();
156: HEAP_INSERT(heap, ++num, int, MY_CMP, MY_HEAP_SWAP);
157: show_heap();
158: bt_assert(is_heap_valid(heap, num));
159: }
160:
161: for (i = 1; i <= MAX_NUM; i++)
162: for (j = 1; j <= MAX_NUM; j++)
163: if(expected[i] == heap[j])
164: break;
165: else if (j == MAX_NUM)
166: {
167: show_heap();
168: bt_abort_msg("Did not find a number %d in heap.", expected[i]);
169: }
170:
171: return 1;
172: }
173:
174: int
175: main(int argc, char *argv[])
176: {
177: bt_init(argc, argv);
178:
179: bt_test_suite(t_heap_insert, "Inserting a descending sequence of numbers (the worst case)");
180: bt_test_suite(t_heap_insert_random, "Inserting pseudo-random numbers");
181: bt_test_suite(t_heap_increase_decrease, "Increasing/Decreasing");
182: bt_test_suite(t_heap_delete, "Deleting");
183: bt_test_suite(t_heap_0, "Is a heap[0] really unused?");
184:
185: return bt_exit_value();
186: }
FreeBSD-CVSweb <freebsd-cvsweb@FreeBSD.org>