1#ifndef joedb_Freedom_Keeper_declared
2#define joedb_Freedom_Keeper_declared
25 Record(
bool is_free,
size_t next,
size_t previous):
33 std::vector<Record> records;
34 enum {used_list = 0, free_list = 1};
39 records[used_list].is_free =
false;
40 records[used_list].next = used_list;
41 records[used_list].previous = used_list;
43 records[free_list].is_free =
true;
44 records[free_list].next = free_list;
45 records[free_list].previous = free_list;
48 bool is_empty()
const {
return used_count == 0;}
50 size_t size()
const {
return records.size() - 2;}
53 size_t get_next(
size_t index)
const {
return records[index].next;}
54 size_t get_previous(
size_t index)
const {
return records[index].previous;}
55 bool is_free(
size_t index)
const {
return records[index].is_free;}
59 index < records.size() &&
60 !records[index].is_free;
66 size_t result = records[free_list].next;
67 if (result == free_list)
70 result = records[free_list].next;
86 const size_t index = records.size();
87 records.emplace_back(
true, records[free_list].next, free_list);
89 records[records[free_list].next].previous = index;
90 records[free_list].next = index;
98 while(
size() < new_size)
109 Record &record = records[index];
110 record.is_free =
false;
112 records[record.previous].next = record.next;
113 records[record.next].previous = record.previous;
115 record.previous = records[used_list].previous;
116 record.next = used_list;
118 records[record.previous].next = index;
119 records[record.next].previous = index;
131 Record &record = records[index];
132 record.is_free =
true;
134 records[record.previous].next = record.next;
135 records[record.next].previous = record.previous;
137 record.next = records[free_list].next;
140 records[records[free_list].next].previous = index;
141 records[free_list].next = index;
153 size_t compact_used_size;
154 size_t compact_free_size;
158 void lose_compactness()
162 while (fk.
size() < compact_free_size)
165 for (
size_t i = 0; i < compact_used_size; i++)
172 compact_used_size(0),
180 return compact_free_size;
188 return compact_used_size == 0;
196 return compact_used_size;
204 return index - 2 < compact_used_size;
212 return index - 2 >= compact_used_size;
221 if (compact_free_size == compact_used_size)
223 return compact_used_size + 2;
233 if (index == compact_used_size + 2 && compact_used_size < compact_free_size)
250 index == compact_used_size + 2 &&
251 compact_used_size +
size <= compact_free_size
254 compact_used_size +=
size;
258 for (
size_t i = 0; i <
size; i++)
267 if (index == compact_used_size + 1 && index > 1)
282 return ++compact_free_size + 1;
296 if (compact_used_size == compact_free_size)
299 return compact_used_size + 2;
309 if (compact_used_size == 0)
328 const size_t result = index + 1;
330 if (result == compact_used_size + 2)
333 if (index == compact_free_size + 2)
348 if (compact_used_size == 0)
351 return compact_used_size + 1;
356 if (compact_used_size == compact_free_size)
359 return compact_free_size + 1;
362 const size_t result = index - 1;
366 if (result == compact_used_size + 1)
378 if (compact_free_size <
size)
379 compact_free_size =
size;
387 if (compact && compact_free_size == compact_used_size)
389 compact_free_size +=
size;
390 compact_used_size +=
size;
394 for (
size_t i = 0; i <
size; i++)
bool is_used(size_t index) const
size_t get_used_count() const
size_t get_first_used() const
void use_vector(size_t index, size_t size)
size_t get_first_free() const
void append_vector(size_t size)
size_t get_previous(size_t index) const
bool is_free(size_t index) const
size_t get_next(size_t index) const
bool is_free(size_t index) const
void resize(size_t new_size)
bool is_used(size_t index) const
size_t get_used_count() const
size_t get_previous(size_t index) const
size_t get_next(size_t index) const
size_t get_first_free() const
size_t get_first_used() const