15 stool::NaiveFLCVector<false> keys;
16 stool::NaiveFLCVector<false> pointers;
19 static constexpr uint64_t ___PermutationLeafSize = 252;
34 using iterator_category = std::bidirectional_iterator_tag;
35 using difference_type = std::ptrdiff_t;
40 return _m_deq->at(this->_m_idx);
45 assert(this->_m_idx < this->_m_deq->size());
74 int16_t sum = (int16_t)this->_m_idx + (int16_t)n;
75 assert((int64_t)sum < (int64_t)this->_m_deq->size());
83 int16_t sum = (int16_t)this->_m_idx - (int16_t)n;
90 return (int16_t)this->_m_idx - (int16_t)other._m_idx;
103 bool operator<(
const PermutationIterator &other)
const {
return this->_m_idx < other._m_idx; }
104 bool operator>(
const PermutationIterator &other)
const {
return this->_m_idx > other._m_idx; }
105 bool operator<=(
const PermutationIterator &other)
const {
return this->_m_idx <= other._m_idx; }
106 bool operator>=(
const PermutationIterator &other)
const {
return this->_m_idx >= other._m_idx; }
113 PermutationIterator begin()
const
117 PermutationIterator end()
const
119 return PermutationIterator(
const_cast<PermutationContainer *
>(
this), this->size());
122 uint64_t size()
const
124 return this->pointers.size();
126 uint64_t size_in_bytes(
bool only_extra_bytes)
const
128 if(only_extra_bytes){
129 return this->keys.size_in_bytes(
true) + this->pointers.size_in_bytes(
true);
131 return sizeof(PermutationContainer) + this->keys.size_in_bytes(
true) + this->pointers.size_in_bytes(
true);
134 uint64_t unused_size_in_bytes()
const
136 return this->keys.unused_size_in_bytes() + this->pointers.unused_size_in_bytes();
140 PermutationItem at(uint64_t pos)
const
142 assert(pos < this->keys.size());
143 assert(pos < this->pointers.size());
145 return PermutationItem(this->pointers.at(pos), this->keys[pos]);
149 std::cout << this->to_string() << std::endl;
155 this->pointers.clear();
157 assert(this->keys.size() == this->pointers.size());
159 void swap(PermutationContainer &item)
161 assert(item.keys.size() == item.pointers.size());
163 this->keys.swap(item.keys);
164 this->pointers.swap(item.pointers);
166 assert(this->keys.size() == this->pointers.size());
168 static std::string name()
172 uint64_t psum([[maybe_unused]] uint64_t i)
const noexcept
176 uint64_t psum() const noexcept
180 int64_t search([[maybe_unused]] uint64_t x)
const noexcept
184 int64_t get_index(
const PermutationItem &&item)
const
186 int64_t size = this->pointers.size();
187 for(int64_t i = 0; i < size; i++){
188 if(this->pointers[i] == item.pointer && this->keys[i] == item.key){
206 std::string to_string()
const
208 assert(this->keys.size() == this->pointers.size());
213 int64_t size = this->pointers.size();
214 for(int64_t i = 0; i < size; i++){
215 s +=
"(" + std::to_string(this->pointers[i]) +
", " + std::to_string(this->keys[i]) +
")";
216 if (i + 1 < (int64_t)this->size())
226 std::vector<PermutationItem> to_value_vector()
const
228 throw std::runtime_error(
"PermutationContainer::NO IMP1");
231 void insert(uint64_t pos, PermutationItem value)
233 this->keys.insert(pos, value.key);
234 this->pointers.insert(pos, value.pointer);
236 assert(this->keys.size() == this->pointers.size());
238 void remove(uint64_t pos)
240 this->keys.remove(pos);
241 this->pointers.remove(pos);
243 assert(this->keys.size() == this->pointers.size());
245 void push_front(
const std::vector<PermutationItem> &new_items)
247 std::vector<uint64_t> tmp_keys;
248 std::vector<uint64_t> tmp_pointers;
249 tmp_keys.resize(new_items.size());
250 tmp_pointers.resize(new_items.size());
252 for (int64_t i = 0; i < (int64_t)new_items.size(); i++)
254 tmp_keys[i] = new_items[i].key;
255 tmp_pointers[i] = new_items[i].pointer;
257 this->keys.push_front_many(tmp_keys);
258 this->pointers.push_front_many(tmp_pointers);
268 assert(this->keys.size() == this->pointers.size());
270 void push_front(
const PermutationItem &new_item)
272 this->keys.push_front(new_item.key);
273 this->pointers.push_front(new_item.pointer);
275 assert(this->keys.size() == this->pointers.size());
278 void push_back(
const std::vector<PermutationItem> &new_items)
280 for (
const PermutationItem &item : new_items)
282 this->keys.push_back(item.key);
283 this->pointers.push_back(item.pointer);
286 assert(this->keys.size() == this->pointers.size());
288 void push_back(PermutationItem value)
290 this->keys.push_back(value.key);
291 this->pointers.push_back(value.pointer);
293 assert(this->keys.size() == this->pointers.size());
295 PermutationItem pop_front()
297 uint64_t key = this->keys[0];
298 uint64_t pointer = this->pointers.head();
299 this->keys.pop_front();
300 this->pointers.pop_front();
302 assert(this->keys.size() == this->pointers.size());
303 return PermutationItem(pointer, key);
306 std::vector<PermutationItem> pop_front(uint64_t len)
308 std::vector<PermutationItem> r;
311 for (uint64_t i = 0; i < len; i++)
313 uint64_t key = this->keys[i];
314 uint64_t pointer = this->pointers[i];
315 r[i] = PermutationItem(pointer, key);
317 this->keys.pop_front_many(len);
318 this->pointers.pop_front_many(len);
320 assert(this->keys.size() == this->pointers.size());
324 PermutationItem pop_back()
326 assert(this->keys.size() > 0 && this->pointers.size() > 0);
327 uint64_t key = this->keys[this->keys.size() - 1];
328 uint64_t pointer = this->pointers.tail();
329 this->keys.pop_back();
330 this->pointers.pop_back();
332 assert(this->keys.size() == this->pointers.size());
333 return PermutationItem(pointer, key);
336 std::vector<PermutationItem> pop_back(uint64_t len)
338 std::vector<PermutationItem> tmp1;
343 tmp1[k--] = this->pop_back();
346 assert(this->keys.size() == this->pointers.size());
349 uint64_t reverse_psum([[maybe_unused]] uint64_t i)
const
353 uint64_t psum([[maybe_unused]] uint64_t i, [[maybe_unused]] uint64_t j)
const
357 uint8_t get_new_key(uint64_t pointer_to_linked_container)
const
359 std::array<uint64_t, 4> occurrence_flag_array;
360 occurrence_flag_array[0] = 0;
361 occurrence_flag_array[1] = 0;
362 occurrence_flag_array[2] = 0;
363 occurrence_flag_array[3] = 0;
366 int64_t size = this->pointers.size();
367 for(int64_t i = 0; i < size; i++){
368 uint64_t pointer = this->pointers[i];
369 if (pointer == pointer_to_linked_container)
371 uint64_t idx = this->keys[i] / 64;
372 uint64_t geta = idx * 64;
374 occurrence_flag_array[idx] = occurrence_flag_array[idx] | (1LL << (63 - (this->keys[i] - geta)));
379 for (uint64_t i = 0; i < 4; i++)
381 if (occurrence_flag_array[i] != UINT64_MAX)
383 uint64_t code_len = stool::LSBByte::get_code_length(~occurrence_flag_array[i]);
384 return (64 * i) + (64 - code_len);
387 throw std::invalid_argument(
"Error(PermutationIterator::get_new_key)");
390 void update_linked_tree(uint64_t ith, uint64_t leaf_index_of_this_container, uint64_t previous_leaf_index, Tree &linked_tree)
392 PermutationItem item = this->at(ith);
393 assert(item.pointer < linked_tree.get_leaf_container_vector_size());
394 PermutationContainer &container = linked_tree.get_leaf_container(item.pointer);
395 int64_t idx = container.get_index(PermutationItem(previous_leaf_index, item.key));
397 uint8_t new_key = container.get_new_key(leaf_index_of_this_container);
402 assert(idx < (int64_t)container.size());
403 container.pointers.set_value(idx, leaf_index_of_this_container);
404 container.keys.set_value(idx, new_key);
405 this->keys.set_value(ith, new_key);
407 assert(this->keys.size() == this->pointers.size());
409 void set_value(uint64_t ith,
const PermutationItem &&item)
411 assert(ith < this->size());
412 this->keys.set_value(ith, item.key);
413 this->pointers.set_value(ith, item.pointer);
415 assert(this->keys.size() == this->pointers.size());
418 static uint64_t get_byte_size(
const PermutationContainer &item)
420 return NaiveFLCVector<false>::get_byte_size(item.keys) + NaiveFLCVector<false>::get_byte_size(item.pointers);
423 static uint64_t get_byte_size(
const std::vector<PermutationContainer> &items)
425 uint64_t bytes =
sizeof(uint64_t);
426 for (
auto &it : items)
428 bytes += PermutationContainer::get_byte_size(it);
433 static void store_to_bytes(
const PermutationContainer &item, std::vector<uint8_t> &output, uint64_t &pos)
435 NaiveFLCVector<false>::store_to_bytes(item.keys, output, pos);
436 NaiveFLCVector<false>::store_to_bytes(item.pointers, output, pos);
438 static void store_to_file(
const PermutationContainer &item, std::ofstream &os)
440 NaiveFLCVector<false>::store_to_file(item.keys, os);
441 NaiveFLCVector<false>::store_to_file(item.pointers, os);
444 static void store_to_bytes(
const std::vector<PermutationContainer> &items, std::vector<uint8_t> &output, uint64_t &pos)
446 uint64_t size = items.size();
447 std::memcpy(output.data() + pos, &size,
sizeof(size));
450 for (
auto &it : items)
452 PermutationContainer::store_to_bytes(it, output, pos);
455 static void store_to_file(
const std::vector<PermutationContainer> &items, std::ofstream &os)
457 uint64_t size = items.size();
458 os.write(
reinterpret_cast<const char *
>(&size),
sizeof(size));
459 for (
auto &it : items)
461 PermutationContainer::store_to_file(it, os);
465 static PermutationContainer load(
const std::vector<uint8_t> &data, uint64_t &pos)
467 PermutationContainer r;
468 NaiveFLCVector<false> tmp1 = NaiveFLCVector<false>::load_from_bytes(data, pos);
469 NaiveFLCVector<false> tmp2 = NaiveFLCVector<false>::load_from_bytes(data, pos);
471 r.pointers.swap(tmp2);
475 static PermutationContainer load(std::ifstream &ifs)
477 PermutationContainer r;
478 NaiveFLCVector<false> tmp1 = NaiveFLCVector<false>::load_from_file(ifs);
479 NaiveFLCVector<false> tmp2 = NaiveFLCVector<false>::load_from_file(ifs);
481 r.pointers.swap(tmp2);
486 static std::vector<PermutationContainer> load_vector_from_bytes(
const std::vector<uint8_t> &data, uint64_t &pos)
489 std::memcpy(&size, data.data() + pos,
sizeof(size));
492 std::vector<PermutationContainer> r;
493 for (uint64_t i = 0; i < size; i++)
495 r.push_back(PermutationContainer::load(data, pos));
499 static std::vector<PermutationContainer> load_vector_from_file(std::ifstream &ifs)
502 ifs.read(
reinterpret_cast<char *
>(&size),
sizeof(size));
504 std::vector<PermutationContainer> r;
505 for (uint64_t i = 0; i < size; i++)
507 r.push_back(PermutationContainer::load(ifs));