Where Online Learning is simpler!
The C and C++ Include Header Files
/usr/include/c++/11/ext/pb_ds/detail/pat_trie_/pat_trie_base.hpp
$ cat -n /usr/include/c++/11/ext/pb_ds/detail/pat_trie_/pat_trie_base.hpp 1 // -*- C++ -*- 2 3 // Copyright (C) 2005-2021 Free Software Foundation, Inc. 4 // 5 // This file is part of the GNU ISO C++ Library. This library is free 6 // software; you can redistribute it and/or modify it under the terms 7 // of the GNU General Public License as published by the Free Software 8 // Foundation; either version 3, or (at your option) any later 9 // version. 10 11 // This library is distributed in the hope that it will be useful, but 12 // WITHOUT ANY WARRANTY; without even the implied warranty of 13 // MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU 14 // General Public License for more details. 15 16 // Under Section 7 of GPL version 3, you are granted additional 17 // permissions described in the GCC Runtime Library Exception, version 18 // 3.1, as published by the Free Software Foundation. 19 20 // You should have received a copy of the GNU General Public License and 21 // a copy of the GCC Runtime Library Exception along with this program; 22 // see the files COPYING3 and COPYING.RUNTIME respectively. If not, see 23 //
. 24 25 // Copyright (C) 2004 Ami Tavory and Vladimir Dreizin, IBM-HRL. 26 27 // Permission to use, copy, modify, sell, and distribute this software 28 // is hereby granted without fee, provided that the above copyright 29 // notice appears in all copies, and that both that copyright notice 30 // and this permission notice appear in supporting documentation. None 31 // of the above authors, nor IBM Haifa Research Laboratories, make any 32 // representation about the suitability of this software for any 33 // purpose. It is provided "as is" without express or implied 34 // warranty. 35 36 /** 37 * @file pat_trie_/pat_trie_base.hpp 38 * Contains the base class for a patricia tree. 39 */ 40 41 #ifndef PB_DS_PAT_TRIE_BASE 42 #define PB_DS_PAT_TRIE_BASE 43 44 #include
45 46 namespace __gnu_pbds 47 { 48 namespace detail 49 { 50 /// Base type for PATRICIA trees. 51 struct pat_trie_base 52 { 53 /** 54 * @brief Three types of nodes. 55 * 56 * i_node is used by _Inode, leaf_node by _Leaf, and head_node by _Head. 57 */ 58 enum node_type 59 { 60 i_node, 61 leaf_node, 62 head_node 63 }; 64 65 /// Metadata base primary template. 66 template
67 struct _Metadata 68 { 69 typedef Metadata metadata_type; 70 typedef _Alloc allocator_type; 71 typedef typename detail::rebind_traits<_Alloc, Metadata>::const_reference 72 const_reference; 73 74 const_reference 75 get_metadata() const 76 { return m_metadata; } 77 78 metadata_type m_metadata; 79 }; 80 81 /// Specialization for null metadata. 82 template
83 struct _Metadata
84 { 85 typedef null_type metadata_type; 86 typedef _Alloc allocator_type; 87 }; 88 89 90 /// Node base. 91 template
92 struct _Node_base 93 : public Metadata 94 { 95 private: 96 typedef typename Metadata::allocator_type _Alloc; 97 98 public: 99 typedef _Alloc allocator_type; 100 typedef _ATraits access_traits; 101 typedef typename _ATraits::type_traits type_traits; 102 typedef typename detail::rebind_traits<_Alloc, _Node_base>::pointer 103 node_pointer; 104 105 node_pointer m_p_parent; 106 const node_type m_type; 107 108 _Node_base(node_type type) : m_type(type) 109 { } 110 111 typedef typename detail::rebind_traits<_Alloc, _ATraits>::const_pointer 112 a_const_pointer; 113 typedef typename _ATraits::const_iterator a_const_iterator; 114 115 #ifdef _GLIBCXX_DEBUG 116 typedef std::pair
node_debug_info; 117 118 void 119 assert_valid(a_const_pointer p_traits, 120 const char* __file, int __line) const 121 { assert_valid_imp(p_traits, __file, __line); } 122 123 virtual node_debug_info 124 assert_valid_imp(a_const_pointer, const char*, int) const = 0; 125 #endif 126 }; 127 128 129 /// Head node for PATRICIA tree. 130 template
131 struct _Head 132 : public _Node_base<_ATraits, Metadata> 133 { 134 typedef _Node_base<_ATraits, Metadata> base_type; 135 typedef typename base_type::type_traits type_traits; 136 typedef typename base_type::node_pointer node_pointer; 137 138 node_pointer m_p_min; 139 node_pointer m_p_max; 140 141 _Head() : base_type(head_node) { } 142 143 #ifdef _GLIBCXX_DEBUG 144 typedef typename base_type::node_debug_info node_debug_info; 145 typedef typename base_type::a_const_pointer a_const_pointer; 146 147 virtual node_debug_info 148 assert_valid_imp(a_const_pointer, const char* __file, int __line) const 149 { 150 _GLIBCXX_DEBUG_VERIFY_AT(false, 151 _M_message("Assertion from %1;:%2;") 152 ._M_string(__FILE__)._M_integer(__LINE__), 153 __file, __line); 154 return node_debug_info(); 155 } 156 #endif 157 }; 158 159 160 /// Leaf node for PATRICIA tree. 161 template
162 struct _Leaf 163 : public _Node_base<_ATraits, Metadata> 164 { 165 typedef _Node_base<_ATraits, Metadata> base_type; 166 typedef typename base_type::type_traits type_traits; 167 typedef typename type_traits::value_type value_type; 168 typedef typename type_traits::reference reference; 169 typedef typename type_traits::const_reference const_reference; 170 171 private: 172 value_type m_value; 173 174 _Leaf(const _Leaf&); 175 176 public: 177 _Leaf(const_reference other) 178 : base_type(leaf_node), m_value(other) { } 179 180 reference 181 value() 182 { return m_value; } 183 184 const_reference 185 value() const 186 { return m_value; } 187 188 #ifdef _GLIBCXX_DEBUG 189 typedef typename base_type::node_debug_info node_debug_info; 190 typedef typename base_type::a_const_pointer a_const_pointer; 191 192 virtual node_debug_info 193 assert_valid_imp(a_const_pointer p_traits, 194 const char* __file, int __line) const 195 { 196 PB_DS_DEBUG_VERIFY(base_type::m_type == leaf_node); 197 node_debug_info ret; 198 const_reference r_val = value(); 199 return std::make_pair(p_traits->begin(p_traits->extract_key(r_val)), 200 p_traits->end(p_traits->extract_key(r_val))); 201 } 202 203 virtual 204 ~_Leaf() { } 205 #endif 206 }; 207 208 209 /// Internal node type, PATRICIA tree. 210 template
211 struct _Inode 212 : public _Node_base<_ATraits, Metadata> 213 { 214 typedef _Node_base<_ATraits, Metadata> base_type; 215 typedef typename base_type::type_traits type_traits; 216 typedef typename base_type::access_traits access_traits; 217 typedef typename type_traits::value_type value_type; 218 typedef typename base_type::allocator_type _Alloc; 219 typedef _Alloc allocator_type; 220 typedef typename _Alloc::size_type size_type; 221 222 private: 223 typedef typename base_type::a_const_pointer a_const_pointer; 224 typedef typename base_type::a_const_iterator a_const_iterator; 225 226 typedef typename base_type::node_pointer node_pointer; 227 typedef typename detail::rebind_traits<_Alloc, base_type>::const_pointer 228 node_const_pointer; 229 230 typedef _Leaf<_ATraits, Metadata> leaf; 231 typedef typename detail::rebind_traits<_Alloc, leaf> __rebind_l; 232 typedef typename __rebind_l::pointer leaf_pointer; 233 typedef typename __rebind_l::const_pointer leaf_const_pointer; 234 235 typedef detail::rebind_traits<_Alloc, _Inode> __rebind_in; 236 typedef typename __rebind_in::pointer inode_pointer; 237 typedef typename __rebind_in::const_pointer inode_const_pointer; 238 239 inline size_type 240 get_pref_pos(a_const_iterator, a_const_iterator, a_const_pointer) const; 241 242 public: 243 typedef detail::rebind_traits<_Alloc, node_pointer> __rebind_np; 244 typedef typename __rebind_np::pointer node_pointer_pointer; 245 typedef typename __rebind_np::reference node_pointer_reference; 246 247 enum 248 { 249 arr_size = _ATraits::max_size + 1 250 }; 251 PB_DS_STATIC_ASSERT(min_arr_size, arr_size >= 2); 252 253 254 /// Constant child iterator. 255 struct const_iterator 256 { 257 node_pointer_pointer m_p_p_cur; 258 node_pointer_pointer m_p_p_end; 259 260 typedef std::forward_iterator_tag iterator_category; 261 typedef typename _Alloc::difference_type difference_type; 262 typedef node_pointer value_type; 263 typedef node_pointer_pointer pointer; 264 typedef node_pointer_reference reference; 265 266 const_iterator(node_pointer_pointer p_p_cur = 0, 267 node_pointer_pointer p_p_end = 0) 268 : m_p_p_cur(p_p_cur), m_p_p_end(p_p_end) 269 { } 270 271 bool 272 operator==(const const_iterator& other) const 273 { return m_p_p_cur == other.m_p_p_cur; } 274 275 bool 276 operator!=(const const_iterator& other) const 277 { return m_p_p_cur != other.m_p_p_cur; } 278 279 const_iterator& 280 operator++() 281 { 282 do 283 ++m_p_p_cur; 284 while (m_p_p_cur != m_p_p_end && *m_p_p_cur == 0); 285 return *this; 286 } 287 288 const_iterator 289 operator++(int) 290 { 291 const_iterator ret_it(*this); 292 operator++(); 293 return ret_it; 294 } 295 296 const node_pointer_pointer 297 operator->() const 298 { 299 _GLIBCXX_DEBUG_ONLY(assert_referencible();) 300 return m_p_p_cur; 301 } 302 303 node_const_pointer 304 operator*() const 305 { 306 _GLIBCXX_DEBUG_ONLY(assert_referencible();) 307 return *m_p_p_cur; 308 } 309 310 protected: 311 #ifdef _GLIBCXX_DEBUG 312 void 313 assert_referencible() const 314 { _GLIBCXX_DEBUG_ASSERT(m_p_p_cur != m_p_p_end && *m_p_p_cur != 0); } 315 #endif 316 }; 317 318 319 /// Child iterator. 320 struct iterator : public const_iterator 321 { 322 public: 323 typedef std::forward_iterator_tag iterator_category; 324 typedef typename _Alloc::difference_type difference_type; 325 typedef node_pointer value_type; 326 typedef node_pointer_pointer pointer; 327 typedef node_pointer_reference reference; 328 329 inline 330 iterator(node_pointer_pointer p_p_cur = 0, 331 node_pointer_pointer p_p_end = 0) 332 : const_iterator(p_p_cur, p_p_end) { } 333 334 bool 335 operator==(const iterator& other) const 336 { return const_iterator::m_p_p_cur == other.m_p_p_cur; } 337 338 bool 339 operator!=(const iterator& other) const 340 { return const_iterator::m_p_p_cur != other.m_p_p_cur; } 341 342 iterator& 343 operator++() 344 { 345 const_iterator::operator++(); 346 return *this; 347 } 348 349 iterator 350 operator++(int) 351 { 352 iterator ret_it(*this); 353 operator++(); 354 return ret_it; 355 } 356 357 node_pointer_pointer 358 operator->() 359 { 360 _GLIBCXX_DEBUG_ONLY(const_iterator::assert_referencible();) 361 return const_iterator::m_p_p_cur; 362 } 363 364 node_pointer 365 operator*() 366 { 367 _GLIBCXX_DEBUG_ONLY(const_iterator::assert_referencible();) 368 return *const_iterator::m_p_p_cur; 369 } 370 }; 371 372 373 _Inode(size_type, const a_const_iterator); 374 375 void 376 update_prefixes(a_const_pointer); 377 378 const_iterator 379 begin() const; 380 381 iterator 382 begin(); 383 384 const_iterator 385 end() const; 386 387 iterator 388 end(); 389 390 inline node_pointer 391 get_child_node(a_const_iterator, a_const_iterator, a_const_pointer); 392 393 inline node_const_pointer 394 get_child_node(a_const_iterator, a_const_iterator, a_const_pointer) const; 395 396 inline iterator 397 get_child_it(a_const_iterator, a_const_iterator, a_const_pointer); 398 399 inline node_pointer 400 get_lower_bound_child_node(a_const_iterator, a_const_iterator, 401 size_type, a_const_pointer); 402 403 inline node_pointer 404 add_child(node_pointer, a_const_iterator, a_const_iterator, 405 a_const_pointer); 406 407 inline node_const_pointer 408 get_join_child(node_const_pointer, a_const_pointer) const; 409 410 inline node_pointer 411 get_join_child(node_pointer, a_const_pointer); 412 413 void 414 remove_child(node_pointer); 415 416 void 417 remove_child(iterator); 418 419 void 420 replace_child(node_pointer, a_const_iterator, a_const_iterator, 421 a_const_pointer); 422 423 inline a_const_iterator 424 pref_b_it() const; 425 426 inline a_const_iterator 427 pref_e_it() const; 428 429 bool 430 should_be_mine(a_const_iterator, a_const_iterator, size_type, 431 a_const_pointer) const; 432 433 leaf_pointer 434 leftmost_descendant(); 435 436 leaf_const_pointer 437 leftmost_descendant() const; 438 439 leaf_pointer 440 rightmost_descendant(); 441 442 leaf_const_pointer 443 rightmost_descendant() const; 444 445 #ifdef _GLIBCXX_DEBUG 446 typedef typename base_type::node_debug_info node_debug_info; 447 448 virtual node_debug_info 449 assert_valid_imp(a_const_pointer, const char*, int) const; 450 #endif 451 452 size_type 453 get_e_ind() const 454 { return m_e_ind; } 455 456 private: 457 _Inode(const _Inode&); 458 459 size_type 460 get_begin_pos() const; 461 462 static __rebind_l s_leaf_alloc; 463 static __rebind_in s_inode_alloc; 464 465 const size_type m_e_ind; 466 a_const_iterator m_pref_b_it; 467 a_const_iterator m_pref_e_it; 468 node_pointer m_a_p_children[arr_size]; 469 }; 470 471 #define PB_DS_CONST_IT_C_DEC \ 472 _CIter
473 474 #define PB_DS_CONST_ODIR_IT_C_DEC \ 475 _CIter
476 477 #define PB_DS_IT_C_DEC \ 478 _Iter
479 480 #define PB_DS_ODIR_IT_C_DEC \ 481 _Iter
482 483 484 /// Const iterator. 485 template
487 class _CIter 488 { 489 public: 490 // These types are all the same for the first four template arguments. 491 typedef typename Node::allocator_type allocator_type; 492 typedef typename Node::type_traits type_traits; 493 494 typedef std::bidirectional_iterator_tag iterator_category; 495 typedef typename allocator_type::difference_type difference_type; 496 typedef typename type_traits::value_type value_type; 497 typedef typename type_traits::pointer pointer; 498 typedef typename type_traits::reference reference; 499 typedef typename type_traits::const_pointer const_pointer; 500 typedef typename type_traits::const_reference const_reference; 501 502 typedef allocator_type _Alloc; 503 typedef typename rebind_traits<_Alloc, Node>::pointer node_pointer; 504 typedef typename rebind_traits<_Alloc, Leaf>::pointer leaf_pointer; 505 typedef typename rebind_traits<_Alloc, Leaf>::const_pointer leaf_const_pointer; 506 typedef typename rebind_traits<_Alloc, Head>::pointer head_pointer; 507 508 typedef typename rebind_traits<_Alloc, Inode>::pointer inode_pointer; 509 typedef typename Inode::iterator inode_iterator; 510 511 node_pointer m_p_nd; 512 513 _CIter(node_pointer p_nd = 0) : m_p_nd(p_nd) 514 { } 515 516 _CIter(const PB_DS_CONST_ODIR_IT_C_DEC& other) 517 : m_p_nd(other.m_p_nd) 518 { } 519 520 _CIter& 521 operator=(const _CIter& other) 522 { 523 m_p_nd = other.m_p_nd; 524 return *this; 525 } 526 527 _CIter& 528 operator=(const PB_DS_CONST_ODIR_IT_C_DEC& other) 529 { 530 m_p_nd = other.m_p_nd; 531 return *this; 532 } 533 534 const_pointer 535 operator->() const 536 { 537 _GLIBCXX_DEBUG_ASSERT(m_p_nd->m_type == leaf_node); 538 return &static_cast
(m_p_nd)->value(); 539 } 540 541 const_reference 542 operator*() const 543 { 544 _GLIBCXX_DEBUG_ASSERT(m_p_nd->m_type == leaf_node); 545 return static_cast
(m_p_nd)->value(); 546 } 547 548 bool 549 operator==(const _CIter& other) const 550 { return m_p_nd == other.m_p_nd; } 551 552 bool 553 operator==(const PB_DS_CONST_ODIR_IT_C_DEC& other) const 554 { return m_p_nd == other.m_p_nd; } 555 556 bool 557 operator!=(const _CIter& other) const 558 { return m_p_nd != other.m_p_nd; } 559 560 bool 561 operator!=(const PB_DS_CONST_ODIR_IT_C_DEC& other) const 562 { return m_p_nd != other.m_p_nd; } 563 564 _CIter& 565 operator++() 566 { 567 inc(integral_constant
()); 568 return *this; 569 } 570 571 _CIter 572 operator++(int) 573 { 574 _CIter ret_it(m_p_nd); 575 operator++(); 576 return ret_it; 577 } 578 579 _CIter& 580 operator--() 581 { 582 dec(integral_constant
()); 583 return *this; 584 } 585 586 _CIter 587 operator--(int) 588 { 589 _CIter ret_it(m_p_nd); 590 operator--(); 591 return ret_it; 592 } 593 594 protected: 595 void 596 inc(false_type) 597 { dec(true_type()); } 598 599 void 600 inc(true_type) 601 { 602 if (m_p_nd->m_type == head_node) 603 { 604 m_p_nd = static_cast
(m_p_nd)->m_p_min; 605 return; 606 } 607 608 node_pointer p_y = m_p_nd->m_p_parent; 609 while (p_y->m_type != head_node && get_larger_sibling(m_p_nd) == 0) 610 { 611 m_p_nd = p_y; 612 p_y = p_y->m_p_parent; 613 } 614 615 if (p_y->m_type == head_node) 616 { 617 m_p_nd = p_y; 618 return; 619 } 620 m_p_nd = leftmost_descendant(get_larger_sibling(m_p_nd)); 621 } 622 623 void 624 dec(false_type) 625 { inc(true_type()); } 626 627 void 628 dec(true_type) 629 { 630 if (m_p_nd->m_type == head_node) 631 { 632 m_p_nd = static_cast
(m_p_nd)->m_p_max; 633 return; 634 } 635 636 node_pointer p_y = m_p_nd->m_p_parent; 637 while (p_y->m_type != head_node && get_smaller_sibling(m_p_nd) == 0) 638 { 639 m_p_nd = p_y; 640 p_y = p_y->m_p_parent; 641 } 642 643 if (p_y->m_type == head_node) 644 { 645 m_p_nd = p_y; 646 return; 647 } 648 m_p_nd = rightmost_descendant(get_smaller_sibling(m_p_nd)); 649 } 650 651 static node_pointer 652 get_larger_sibling(node_pointer p_nd) 653 { 654 inode_pointer p_parent = static_cast
(p_nd->m_p_parent); 655 656 inode_iterator it = p_parent->begin(); 657 while (*it != p_nd) 658 ++it; 659 660 inode_iterator next_it = it; 661 ++next_it; 662 return (next_it == p_parent->end())? 0 : *next_it; 663 } 664 665 static node_pointer 666 get_smaller_sibling(node_pointer p_nd) 667 { 668 inode_pointer p_parent = static_cast
(p_nd->m_p_parent); 669 670 inode_iterator it = p_parent->begin(); 671 if (*it == p_nd) 672 return 0; 673 674 inode_iterator prev_it; 675 do 676 { 677 prev_it = it; 678 ++it; 679 if (*it == p_nd) 680 return *prev_it; 681 } 682 while (true); 683 684 _GLIBCXX_DEBUG_ASSERT(false); 685 return 0; 686 } 687 688 static leaf_pointer 689 leftmost_descendant(node_pointer p_nd) 690 { 691 if (p_nd->m_type == leaf_node) 692 return static_cast
(p_nd); 693 return static_cast
(p_nd)->leftmost_descendant(); 694 } 695 696 static leaf_pointer 697 rightmost_descendant(node_pointer p_nd) 698 { 699 if (p_nd->m_type == leaf_node) 700 return static_cast
(p_nd); 701 return static_cast
(p_nd)->rightmost_descendant(); 702 } 703 }; 704 705 706 /// Iterator. 707 template
709 class _Iter 710 : public _CIter
711 { 712 public: 713 typedef _CIter
714 base_type; 715 typedef typename base_type::allocator_type allocator_type; 716 typedef typename base_type::type_traits type_traits; 717 typedef typename type_traits::value_type value_type; 718 typedef typename type_traits::pointer pointer; 719 typedef typename type_traits::reference reference; 720 721 typedef typename base_type::node_pointer node_pointer; 722 typedef typename base_type::leaf_pointer leaf_pointer; 723 typedef typename base_type::leaf_const_pointer leaf_const_pointer; 724 typedef typename base_type::head_pointer head_pointer; 725 typedef typename base_type::inode_pointer inode_pointer; 726 727 _Iter(node_pointer p_nd = 0) 728 : base_type(p_nd) { } 729 730 _Iter(const PB_DS_ODIR_IT_C_DEC& other) 731 : base_type(other.m_p_nd) { } 732 733 _Iter& 734 operator=(const _Iter& other) 735 { 736 base_type::m_p_nd = other.m_p_nd; 737 return *this; 738 } 739 740 _Iter& 741 operator=(const PB_DS_ODIR_IT_C_DEC& other) 742 { 743 base_type::m_p_nd = other.m_p_nd; 744 return *this; 745 } 746 747 pointer 748 operator->() const 749 { 750 _GLIBCXX_DEBUG_ASSERT(base_type::m_p_nd->m_type == leaf_node); 751 return &static_cast
(base_type::m_p_nd)->value(); 752 } 753 754 reference 755 operator*() const 756 { 757 _GLIBCXX_DEBUG_ASSERT(base_type::m_p_nd->m_type == leaf_node); 758 return static_cast
(base_type::m_p_nd)->value(); 759 } 760 761 _Iter& 762 operator++() 763 { 764 base_type::operator++(); 765 return *this; 766 } 767 768 _Iter 769 operator++(int) 770 { 771 _Iter ret(base_type::m_p_nd); 772 operator++(); 773 return ret; 774 } 775 776 _Iter& 777 operator--() 778 { 779 base_type::operator--(); 780 return *this; 781 } 782 783 _Iter 784 operator--(int) 785 { 786 _Iter ret(base_type::m_p_nd); 787 operator--(); 788 return ret; 789 } 790 }; 791 792 #undef PB_DS_CONST_ODIR_IT_C_DEC 793 #undef PB_DS_ODIR_IT_C_DEC 794 795 796 #define PB_DS_PAT_TRIE_NODE_CONST_ITERATOR_C_DEC \ 797 _Node_citer
798 799 #define PB_DS_PAT_TRIE_NODE_ITERATOR_C_DEC \ 800 _Node_iter
801 802 /// Node const iterator. 803 template
810 class _Node_citer 811 { 812 protected: 813 typedef typename rebind_traits<_Alloc, Node>::pointer node_pointer; 814 815 typedef typename rebind_traits<_Alloc, Leaf>::pointer leaf_pointer; 816 typedef typename rebind_traits<_Alloc, Leaf>::const_pointer leaf_const_pointer; 817 818 typedef typename rebind_traits<_Alloc, Inode>::pointer inode_pointer; 819 typedef typename rebind_traits<_Alloc, Inode>::const_pointer inode_const_pointer; 820 821 typedef typename Node::a_const_pointer a_const_pointer; 822 typedef typename Node::a_const_iterator a_const_iterator; 823 824 private: 825 a_const_iterator 826 pref_begin() const 827 { 828 if (m_p_nd->m_type == leaf_node) 829 { 830 leaf_const_pointer lcp = static_cast
(m_p_nd); 831 return m_p_traits->begin(m_p_traits->extract_key(lcp->value())); 832 } 833 _GLIBCXX_DEBUG_ASSERT(m_p_nd->m_type == i_node); 834 return static_cast
(m_p_nd)->pref_b_it(); 835 } 836 837 a_const_iterator 838 pref_end() const 839 { 840 if (m_p_nd->m_type == leaf_node) 841 { 842 leaf_const_pointer lcp = static_cast
(m_p_nd); 843 return m_p_traits->end(m_p_traits->extract_key(lcp->value())); 844 } 845 _GLIBCXX_DEBUG_ASSERT(m_p_nd->m_type == i_node); 846 return static_cast
(m_p_nd)->pref_e_it(); 847 } 848 849 public: 850 typedef trivial_iterator_tag iterator_category; 851 typedef trivial_iterator_difference_type difference_type; 852 typedef typename _Alloc::size_type size_type; 853 854 typedef _CIterator value_type; 855 typedef value_type reference; 856 typedef value_type const_reference; 857 858 /// Metadata type. 859 typedef typename Node::metadata_type metadata_type; 860 861 /// Const metadata reference type. 862 typedef typename rebind_traits<_Alloc, metadata_type>::const_reference metadata_const_reference; 863 864 inline 865 _Node_citer(node_pointer p_nd = 0, a_const_pointer p_traits = 0) 866 : m_p_nd(const_cast
(p_nd)), m_p_traits(p_traits) 867 { } 868 869 /// Subtree valid prefix. 870 std::pair
871 valid_prefix() const 872 { return std::make_pair(pref_begin(), pref_end()); } 873 874 /// Const access; returns the __const iterator* associated with 875 /// the current leaf. 876 const_reference 877 operator*() const 878 { 879 _GLIBCXX_DEBUG_ASSERT(num_children() == 0); 880 return _CIterator(m_p_nd); 881 } 882 883 /// Metadata access. 884 metadata_const_reference 885 get_metadata() const 886 { return m_p_nd->get_metadata(); } 887 888 /// Returns the number of children in the corresponding node. 889 size_type 890 num_children() const 891 { 892 if (m_p_nd->m_type == leaf_node) 893 return 0; 894 _GLIBCXX_DEBUG_ASSERT(m_p_nd->m_type == i_node); 895 inode_pointer inp = static_cast
(m_p_nd); 896 return std::distance(inp->begin(), inp->end()); 897 } 898 899 /// Returns a __const node __iterator to the corresponding node's 900 /// i-th child. 901 _Node_citer 902 get_child(size_type i) const 903 { 904 _GLIBCXX_DEBUG_ASSERT(m_p_nd->m_type == i_node); 905 inode_pointer inp = static_cast
(m_p_nd); 906 typename Inode::iterator it = inp->begin(); 907 std::advance(it, i); 908 return _Node_citer(*it, m_p_traits); 909 } 910 911 /// Compares content to a different iterator object. 912 bool 913 operator==(const _Node_citer& other) const 914 { return m_p_nd == other.m_p_nd; } 915 916 /// Compares content (negatively) to a different iterator object. 917 bool 918 operator!=(const _Node_citer& other) const 919 { return m_p_nd != other.m_p_nd; } 920 921 node_pointer m_p_nd; 922 a_const_pointer m_p_traits; 923 }; 924 925 926 /// Node iterator. 927 template
934 class _Node_iter 935 : public _Node_citer
936 { 937 private: 938 typedef _Node_citer
base_type; 940 typedef typename rebind_traits<_Alloc, Node>::pointer node_pointer; 941 typedef typename base_type::inode_pointer inode_pointer; 942 typedef typename base_type::a_const_pointer a_const_pointer; 943 typedef Iterator iterator; 944 945 public: 946 typedef typename base_type::size_type size_type; 947 948 typedef Iterator value_type; 949 typedef value_type reference; 950 typedef value_type const_reference; 951 952 _Node_iter(node_pointer p_nd = 0, a_const_pointer p_traits = 0) 953 : base_type(p_nd, p_traits) 954 { } 955 956 /// Access; returns the iterator* associated with the current leaf. 957 reference 958 operator*() const 959 { 960 _GLIBCXX_DEBUG_ASSERT(base_type::num_children() == 0); 961 return iterator(base_type::m_p_nd); 962 } 963 964 /// Returns a node __iterator to the corresponding node's i-th child. 965 _Node_iter 966 get_child(size_type i) const 967 { 968 _GLIBCXX_DEBUG_ASSERT(base_type::m_p_nd->m_type == i_node); 969 970 typename Inode::iterator it = 971 static_cast
(base_type::m_p_nd)->begin(); 972 973 std::advance(it, i); 974 return _Node_iter(*it, base_type::m_p_traits); 975 } 976 }; 977 }; 978 979 980 #define PB_DS_CLASS_T_DEC \ 981 template
982 983 #define PB_DS_CLASS_C_DEC \ 984 pat_trie_base::_Inode<_ATraits, Metadata> 985 986 PB_DS_CLASS_T_DEC 987 typename PB_DS_CLASS_C_DEC::__rebind_l 988 PB_DS_CLASS_C_DEC::s_leaf_alloc; 989 990 PB_DS_CLASS_T_DEC 991 typename PB_DS_CLASS_C_DEC::__rebind_in 992 PB_DS_CLASS_C_DEC::s_inode_alloc; 993 994 PB_DS_CLASS_T_DEC 995 inline typename PB_DS_CLASS_C_DEC::size_type 996 PB_DS_CLASS_C_DEC:: 997 get_pref_pos(a_const_iterator b_it, a_const_iterator e_it, 998 a_const_pointer p_traits) const 999 { 1000 if (static_cast
(std::distance(b_it, e_it)) <= m_e_ind) 1001 return 0; 1002 std::advance(b_it, m_e_ind); 1003 return 1 + p_traits->e_pos(*b_it); 1004 } 1005 1006 PB_DS_CLASS_T_DEC 1007 PB_DS_CLASS_C_DEC:: 1008 _Inode(size_type len, const a_const_iterator it) 1009 : base_type(i_node), m_e_ind(len), m_pref_b_it(it), m_pref_e_it(it) 1010 { 1011 std::advance(m_pref_e_it, m_e_ind); 1012 std::fill(m_a_p_children, m_a_p_children + arr_size, 1013 static_cast
(0)); 1014 } 1015 1016 PB_DS_CLASS_T_DEC 1017 void 1018 PB_DS_CLASS_C_DEC:: 1019 update_prefixes(a_const_pointer p_traits) 1020 { 1021 node_pointer p_first = *begin(); 1022 if (p_first->m_type == leaf_node) 1023 { 1024 leaf_const_pointer p = static_cast
(p_first); 1025 m_pref_b_it = p_traits->begin(access_traits::extract_key(p->value())); 1026 } 1027 else 1028 { 1029 inode_pointer p = static_cast
(p_first); 1030 _GLIBCXX_DEBUG_ASSERT(p_first->m_type == i_node); 1031 m_pref_b_it = p->pref_b_it(); 1032 } 1033 m_pref_e_it = m_pref_b_it; 1034 std::advance(m_pref_e_it, m_e_ind); 1035 } 1036 1037 PB_DS_CLASS_T_DEC 1038 typename PB_DS_CLASS_C_DEC::const_iterator 1039 PB_DS_CLASS_C_DEC:: 1040 begin() const 1041 { 1042 typedef node_pointer_pointer pointer_type; 1043 pointer_type p = const_cast
(m_a_p_children); 1044 return const_iterator(p + get_begin_pos(), p + arr_size); 1045 } 1046 1047 PB_DS_CLASS_T_DEC 1048 typename PB_DS_CLASS_C_DEC::iterator 1049 PB_DS_CLASS_C_DEC:: 1050 begin() 1051 { 1052 return iterator(m_a_p_children + get_begin_pos(), 1053 m_a_p_children + arr_size); 1054 } 1055 1056 PB_DS_CLASS_T_DEC 1057 typename PB_DS_CLASS_C_DEC::const_iterator 1058 PB_DS_CLASS_C_DEC:: 1059 end() const 1060 { 1061 typedef node_pointer_pointer pointer_type; 1062 pointer_type p = const_cast
(m_a_p_children) + arr_size; 1063 return const_iterator(p, p); 1064 } 1065 1066 PB_DS_CLASS_T_DEC 1067 typename PB_DS_CLASS_C_DEC::iterator 1068 PB_DS_CLASS_C_DEC:: 1069 end() 1070 { return iterator(m_a_p_children + arr_size, m_a_p_children + arr_size); } 1071 1072 PB_DS_CLASS_T_DEC 1073 inline typename PB_DS_CLASS_C_DEC::node_pointer 1074 PB_DS_CLASS_C_DEC:: 1075 get_child_node(a_const_iterator b_it, a_const_iterator e_it, 1076 a_const_pointer p_traits) 1077 { 1078 const size_type i = get_pref_pos(b_it, e_it, p_traits); 1079 _GLIBCXX_DEBUG_ASSERT(i < arr_size); 1080 return m_a_p_children[i]; 1081 } 1082 1083 PB_DS_CLASS_T_DEC 1084 inline typename PB_DS_CLASS_C_DEC::iterator 1085 PB_DS_CLASS_C_DEC:: 1086 get_child_it(a_const_iterator b_it, a_const_iterator e_it, 1087 a_const_pointer p_traits) 1088 { 1089 const size_type i = get_pref_pos(b_it, e_it, p_traits); 1090 _GLIBCXX_DEBUG_ASSERT(i < arr_size); 1091 _GLIBCXX_DEBUG_ASSERT(m_a_p_children[i] != 0); 1092 return iterator(m_a_p_children + i, m_a_p_children + i); 1093 } 1094 1095 PB_DS_CLASS_T_DEC 1096 inline typename PB_DS_CLASS_C_DEC::node_const_pointer 1097 PB_DS_CLASS_C_DEC:: 1098 get_child_node(a_const_iterator b_it, a_const_iterator e_it, 1099 a_const_pointer p_traits) const 1100 { return const_cast
(get_child_node(b_it, e_it, p_traits)); } 1101 1102 PB_DS_CLASS_T_DEC 1103 typename PB_DS_CLASS_C_DEC::node_pointer 1104 PB_DS_CLASS_C_DEC:: 1105 get_lower_bound_child_node(a_const_iterator b_it, a_const_iterator e_it, 1106 size_type checked_ind, 1107 a_const_pointer p_traits) 1108 { 1109 if (!should_be_mine(b_it, e_it, checked_ind, p_traits)) 1110 { 1111 if (p_traits->cmp_prefixes(b_it, e_it, m_pref_b_it, 1112 m_pref_e_it, true)) 1113 return leftmost_descendant(); 1114 return rightmost_descendant(); 1115 } 1116 1117 size_type i = get_pref_pos(b_it, e_it, p_traits); 1118 _GLIBCXX_DEBUG_ASSERT(i < arr_size); 1119 1120 if (m_a_p_children[i] != 0) 1121 return m_a_p_children[i]; 1122 1123 while (++i < arr_size) 1124 if (m_a_p_children[i] != 0) 1125 { 1126 const node_type& __nt = m_a_p_children[i]->m_type; 1127 node_pointer ret = m_a_p_children[i]; 1128 1129 if (__nt == leaf_node) 1130 return ret; 1131 1132 _GLIBCXX_DEBUG_ASSERT(__nt == i_node); 1133 inode_pointer inp = static_cast
(ret); 1134 return inp->leftmost_descendant(); 1135 } 1136 1137 return rightmost_descendant(); 1138 } 1139 1140 PB_DS_CLASS_T_DEC 1141 inline typename PB_DS_CLASS_C_DEC::node_pointer 1142 PB_DS_CLASS_C_DEC:: 1143 add_child(node_pointer p_nd, a_const_iterator b_it, a_const_iterator e_it, 1144 a_const_pointer p_traits) 1145 { 1146 const size_type i = get_pref_pos(b_it, e_it, p_traits); 1147 _GLIBCXX_DEBUG_ASSERT(i < arr_size); 1148 if (m_a_p_children[i] == 0) 1149 { 1150 m_a_p_children[i] = p_nd; 1151 p_nd->m_p_parent = this; 1152 return p_nd; 1153 } 1154 return m_a_p_children[i]; 1155 } 1156 1157 PB_DS_CLASS_T_DEC 1158 typename PB_DS_CLASS_C_DEC::node_const_pointer 1159 PB_DS_CLASS_C_DEC:: 1160 get_join_child(node_const_pointer p_nd, 1161 a_const_pointer p_tr) const 1162 { 1163 node_pointer p = const_cast
(p_nd); 1164 return const_cast
(this)->get_join_child(p, p_tr); 1165 } 1166 1167 PB_DS_CLASS_T_DEC 1168 typename PB_DS_CLASS_C_DEC::node_pointer 1169 PB_DS_CLASS_C_DEC:: 1170 get_join_child(node_pointer p_nd, a_const_pointer p_traits) 1171 { 1172 size_type i; 1173 a_const_iterator b_it; 1174 a_const_iterator e_it; 1175 if (p_nd->m_type == leaf_node) 1176 { 1177 leaf_const_pointer p = static_cast
(p_nd); 1178 1179 typedef typename type_traits::key_const_reference kcr; 1180 kcr r_key = access_traits::extract_key(p->value()); 1181 b_it = p_traits->begin(r_key); 1182 e_it = p_traits->end(r_key); 1183 } 1184 else 1185 { 1186 b_it = static_cast
(p_nd)->pref_b_it(); 1187 e_it = static_cast
(p_nd)->pref_e_it(); 1188 } 1189 i = get_pref_pos(b_it, e_it, p_traits); 1190 _GLIBCXX_DEBUG_ASSERT(i < arr_size); 1191 return m_a_p_children[i]; 1192 } 1193 1194 PB_DS_CLASS_T_DEC 1195 void 1196 PB_DS_CLASS_C_DEC:: 1197 remove_child(node_pointer p_nd) 1198 { 1199 size_type i = 0; 1200 for (; i < arr_size; ++i) 1201 if (m_a_p_children[i] == p_nd) 1202 { 1203 m_a_p_children[i] = 0; 1204 return; 1205 } 1206 _GLIBCXX_DEBUG_ASSERT(i != arr_size); 1207 } 1208 1209 PB_DS_CLASS_T_DEC 1210 void 1211 PB_DS_CLASS_C_DEC:: 1212 remove_child(iterator it) 1213 { *it.m_p_p_cur = 0; } 1214 1215 PB_DS_CLASS_T_DEC 1216 void 1217 PB_DS_CLASS_C_DEC:: 1218 replace_child(node_pointer p_nd, a_const_iterator b_it, 1219 a_const_iterator e_it, 1220 a_const_pointer p_traits) 1221 { 1222 const size_type i = get_pref_pos(b_it, e_it, p_traits); 1223 _GLIBCXX_DEBUG_ASSERT(i < arr_size); 1224 m_a_p_children[i] = p_nd; 1225 p_nd->m_p_parent = this; 1226 } 1227 1228 PB_DS_CLASS_T_DEC 1229 inline typename PB_DS_CLASS_C_DEC::a_const_iterator 1230 PB_DS_CLASS_C_DEC:: 1231 pref_b_it() const 1232 { return m_pref_b_it; } 1233 1234 PB_DS_CLASS_T_DEC 1235 inline typename PB_DS_CLASS_C_DEC::a_const_iterator 1236 PB_DS_CLASS_C_DEC:: 1237 pref_e_it() const 1238 { return m_pref_e_it; } 1239 1240 PB_DS_CLASS_T_DEC 1241 bool 1242 PB_DS_CLASS_C_DEC:: 1243 should_be_mine(a_const_iterator b_it, a_const_iterator e_it, 1244 size_type checked_ind, 1245 a_const_pointer p_traits) const 1246 { 1247 if (m_e_ind == 0) 1248 return true; 1249 1250 const size_type num_es = std::distance(b_it, e_it); 1251 if (num_es < m_e_ind) 1252 return false; 1253 1254 a_const_iterator key_b_it = b_it; 1255 std::advance(key_b_it, checked_ind); 1256 a_const_iterator key_e_it = b_it; 1257 std::advance(key_e_it, m_e_ind); 1258 1259 a_const_iterator value_b_it = m_pref_b_it; 1260 std::advance(value_b_it, checked_ind); 1261 a_const_iterator value_e_it = m_pref_b_it; 1262 std::advance(value_e_it, m_e_ind); 1263 1264 return p_traits->equal_prefixes(key_b_it, key_e_it, value_b_it, 1265 value_e_it); 1266 } 1267 1268 PB_DS_CLASS_T_DEC 1269 typename PB_DS_CLASS_C_DEC::leaf_pointer 1270 PB_DS_CLASS_C_DEC:: 1271 leftmost_descendant() 1272 { 1273 node_pointer p_pot = *begin(); 1274 if (p_pot->m_type == leaf_node) 1275 return (static_cast
(p_pot)); 1276 _GLIBCXX_DEBUG_ASSERT(p_pot->m_type == i_node); 1277 return static_cast
(p_pot)->leftmost_descendant(); 1278 } 1279 1280 PB_DS_CLASS_T_DEC 1281 typename PB_DS_CLASS_C_DEC::leaf_const_pointer 1282 PB_DS_CLASS_C_DEC:: 1283 leftmost_descendant() const 1284 { return const_cast
(this)->leftmost_descendant(); } 1285 1286 PB_DS_CLASS_T_DEC 1287 typename PB_DS_CLASS_C_DEC::leaf_pointer 1288 PB_DS_CLASS_C_DEC:: 1289 rightmost_descendant() 1290 { 1291 const size_type num_children = std::distance(begin(), end()); 1292 _GLIBCXX_DEBUG_ASSERT(num_children >= 2); 1293 1294 iterator it = begin(); 1295 std::advance(it, num_children - 1); 1296 node_pointer p_pot =* it; 1297 if (p_pot->m_type == leaf_node) 1298 return static_cast
(p_pot); 1299 _GLIBCXX_DEBUG_ASSERT(p_pot->m_type == i_node); 1300 return static_cast
(p_pot)->rightmost_descendant(); 1301 } 1302 1303 PB_DS_CLASS_T_DEC 1304 typename PB_DS_CLASS_C_DEC::leaf_const_pointer 1305 PB_DS_CLASS_C_DEC:: 1306 rightmost_descendant() const 1307 { return const_cast
(this)->rightmost_descendant(); } 1308 1309 PB_DS_CLASS_T_DEC 1310 typename PB_DS_CLASS_C_DEC::size_type 1311 PB_DS_CLASS_C_DEC:: 1312 get_begin_pos() const 1313 { 1314 size_type i = 0; 1315 for (; i < arr_size && m_a_p_children[i] == 0; ++i) 1316 ; 1317 return i; 1318 } 1319 1320 #ifdef _GLIBCXX_DEBUG 1321 PB_DS_CLASS_T_DEC 1322 typename PB_DS_CLASS_C_DEC::node_debug_info 1323 PB_DS_CLASS_C_DEC:: 1324 assert_valid_imp(a_const_pointer p_traits, 1325 const char* __file, int __line) const 1326 { 1327 PB_DS_DEBUG_VERIFY(base_type::m_type == i_node); 1328 PB_DS_DEBUG_VERIFY(static_cast
(std::distance(pref_b_it(), pref_e_it())) == m_e_ind); 1329 PB_DS_DEBUG_VERIFY(std::distance(begin(), end()) >= 2); 1330 1331 for (typename _Inode::const_iterator it = begin(); it != end(); ++it) 1332 { 1333 node_const_pointer p_nd = *it; 1334 PB_DS_DEBUG_VERIFY(p_nd->m_p_parent == this); 1335 node_debug_info child_ret = p_nd->assert_valid_imp(p_traits, 1336 __file, __line); 1337 1338 PB_DS_DEBUG_VERIFY(static_cast
(std::distance(child_ret.first, child_ret.second)) >= m_e_ind); 1339 PB_DS_DEBUG_VERIFY(should_be_mine(child_ret.first, child_ret.second, 0, p_traits)); 1340 PB_DS_DEBUG_VERIFY(get_pref_pos(child_ret.first, child_ret.second, p_traits) == static_cast
(it.m_p_p_cur - m_a_p_children)); 1341 } 1342 return std::make_pair(pref_b_it(), pref_e_it()); 1343 } 1344 #endif 1345 1346 #undef PB_DS_CLASS_T_DEC 1347 #undef PB_DS_CLASS_C_DEC 1348 } // namespace detail 1349 } // namespace __gnu_pbds 1350 1351 #endif
Contact us
|
About us
|
Term of use
|
Copyright © 2000-2025 MyWebUniversity.com ™