Aleph-w 3.0
A C++ Library for Data Structures and Algorithms
Loading...
Searching...
No Matches
tpl_treap.H
Go to the documentation of this file.
1
2/*
3 Aleph_w
4
5 Data structures & Algorithms
6 version 2.0.0b
7 https://github.com/lrleon/Aleph-w
8
9 This file is part of Aleph-w library
10
11 Copyright (c) 2002-2026 Leandro Rabindranath Leon
12
13 Permission is hereby granted, free of charge, to any person obtaining a copy
14 of this software and associated documentation files (the "Software"), to deal
15 in the Software without restriction, including without limitation the rights
16 to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
17 copies of the Software, and to permit persons to whom the Software is
18 furnished to do so, subject to the following conditions:
19
20 The above copyright notice and this permission notice shall be included in all
21 copies or substantial portions of the Software.
22
23 THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
24 IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
25 FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
26 AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
27 LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
28 OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
29 SOFTWARE.
30*/
31
32
52# ifndef TPL_TREAP_H
53# define TPL_TREAP_H
54
55# include <gsl/gsl_rng.h>
56# include <ahFunction.H>
57# include <tpl_binNodeUtils.H>
58# include <treapNode.H>
59# include <tpl_binTreeOps.H>
60# include <ah-errors.H>
61# include <ah-concepts.H>
62
63using namespace Aleph;
64
65namespace Aleph
66{
147 template <template <typename> class NodeType, typename Key, class Compare>
150 {
151 public:
153
154 private:
159 Compare cmp;
160
161 void init(const unsigned int seed)
162 {
165
166 ah_bad_alloc_if(r == nullptr);
167
169 }
170
171 public:
173 void set_seed(const unsigned long seed) noexcept { gsl_rng_set(r, seed); }
174
176 void swap(Gen_Treap & tree) noexcept
177 {
178 std::swap(tree_root, tree.tree_root);
179 std::swap(cmp, tree.cmp);
180 std::swap(r, tree.r);
181 }
182
184 Compare &key_comp() noexcept { return cmp; }
185
187 Compare &get_compare() noexcept { return key_comp(); }
188
191 Gen_Treap(const unsigned long seed, const Compare & __cmp = Compare())
193 {
194 init(seed);
195 }
196
199 Gen_Treap(const Compare & cmp = Compare())
201 { /* empty */
202 }
203
205 {
206 if (r != nullptr)
208 }
209
212
215
222 Node * search(const Key & key) const noexcept
223 {
225 return ret_val == Node::NullPtr ? nullptr : ret_val;
226 }
227
228 private:
229 Node * insert(Node *root, Node *p) noexcept
230 {
231 if (root == Node::NullPtr)
232 return p;
233
234 const Key & pk = KEY(p);
235 const Key & rk = KEY(root);
236 Node *insertion_result = nullptr;
237 if (cmp(pk, rk))
238 {
240 if (insertion_result == Node::NullPtr)
241 return Node::NullPtr;
242
245 return rotate_to_right(root);
246 return root;
247 }
248 if (cmp(rk, pk))
249 {
251 if (insertion_result == Node::NullPtr)
252 return Node::NullPtr;
253
256 return rotate_to_left(root);
257 return root;
258 }
259
260 return Node::NullPtr;
261 }
262
263 Node * search_or_insert(Node *& root, Node *p) noexcept
264 {
265 if (root == Node::NullPtr)
266 return root = p;
267
268 const Key & pk = KEY(p);
269 const Key & rk = KEY(root);
270 if (cmp(pk, rk))
271 {
273 if (ret == p) // p was inserted?
274 if (PRIO(LLINK(root)) < PRIO(root))
276
277 return ret;
278 }
279 if (cmp(rk, pk))
280 {
282 if (ret == p) // p was inserted?
283 if (PRIO(RLINK(root)) < PRIO(root))
285
286 return ret;
287 }
288
289 return root;
290 }
291
292 Node * insert_dup(Node *root, Node *p) noexcept
293 {
294 if (root == Node::NullPtr)
295 return p;
296
297 const Key & pk = KEY(p);
298 const Key & rk = KEY(root);
299 if (cmp(pk, rk))
300 {
301 if (Node *result = LLINK(root) = insert_dup(LLINK(root), p); PRIO(result) < PRIO(root))
302 return rotate_to_right(root);
303 return root;
304 }
305 if (Node *result = RLINK(root) = insert_dup(RLINK(root), p); PRIO(result) < PRIO(root))
306 return rotate_to_left(root);
307 return root;
308 }
309
310 public:
320 Node * insert(Node *p) noexcept
321 {
322 assert(p != Node::NullPtr);
323
324 PRIO(p) = gsl_rng_get(r); // Priority Random Selection
325 Node *result = insert(tree_root, p);
326 if (result == Node::NullPtr)
327 return nullptr;
328
329 tree_root = result;
330
331 return p;
332 }
333
347 {
348 assert(p != Node::NullPtr);
349
350 PRIO(p) = gsl_rng_get(r); // Priority Random Selection
351
352 return search_or_insert(tree_root, p);
353 }
354
362 Node * insert_dup(Node *p) noexcept
363 {
364 assert(p != Node::NullPtr);
365
366 PRIO(p) = gsl_rng_get(r); // Priority Random Selection
368
369 return p;
370 }
371
374
381 Node * remove(const Key & key) noexcept
382 {
383 Node **pp = &RLINK(head_ptr);
384 Node *p = tree_root;
385
386 while (p != Node::NullPtr) // descender buscando la clave
387 {
388 const Key & pk = KEY(p);
389 if (cmp(key, pk))
390 {
391 pp = &LLINK(p);
392 p = LLINK(p);
393 }
394 else if (cmp(pk, key))
395 {
396 pp = &RLINK(p);
397 p = RLINK(p);
398 }
399 else
400 break; //found!
401 }
402
403 if (p == Node::NullPtr)
404 return nullptr; // Key was not found
405
406 // rotate p until it becomes a leaf
407 while (not (LLINK(p) == Node::NullPtr and RLINK(p) == Node::NullPtr))
408 if (PRIO(LLINK(p)) < PRIO(RLINK(p)))
409 {
410 *pp = rotate_to_right(p);
411 pp = &RLINK(*pp);
412 }
413 else
414 {
415 *pp = rotate_to_left(p);
416 pp = &LLINK(*pp);
417 }
418
419 *pp = Node::NullPtr;
420
421 p->reset();
422
423 return p;
424 }
425
426 private:
427 static Node * join_exclusive(Node *t1, Node *t2) noexcept
428 {
429 if (t1 == Node::NullPtr)
430 return t2;
431
432 if (t2 == Node::NullPtr)
433 return t1;
434
435 if (PRIO(t1) < PRIO(t2))
436 {
438 return t1;
439 }
441 return t2;
442 }
443
444 Node * remove(Node *& root, const Key & key) noexcept
445 {
446 if (root == Node::NullPtr)
447 return Node::NullPtr;
448
449 const Key & rk = KEY(root);
450 if (cmp(key, rk))
451 return remove(LLINK(root), key);
452 if (cmp(rk, key))
453 return remove(RLINK(root), key);
454
455 Node *ret = root; // key found!
457 ret->reset();
458
459 return ret;
460 }
461
462 void join_dup(Node *& t1, Node *t2) noexcept
463 {
464 if (t2 == Node::NullPtr)
465 return;
466
467 Node *l = LLINK(t2), *r = RLINK(t2);
468 t2->reset();
469 t1 = insert_dup(t1, t2);
470 join_dup(t1, l);
471 join_dup(t1, r);
472 }
473
474 void join(Node *& t1, Node *t2, Node *& dup) noexcept
475 {
476 if (t2 == Node::NullPtr)
477 return;
478
479 Node *l = LLINK(t2), *r = RLINK(t2);
480 t2->reset();
481 ins:
482 Node *ret = insert(t1, t2);
483 if (ret == Node::NullPtr)
484 {
485 dup = insert_dup(dup, remove(t1, KEY(t2)));
486 goto ins;
487 }
488
489 t1 = ret;
490 join(t1, l, dup);
491 join(t1, r, dup);
492 }
493
494 public:
507 void join(Gen_Treap & t, Gen_Treap & dup) noexcept
508 {
509 join(tree_root, t.tree_root, dup.tree_root);
510 t.tree_root = Node::NullPtr;
511 }
512
521 void join_dup(Gen_Treap & t) noexcept
522 {
523 join_dup(tree_root, t.tree_root);
524 t.tree_root = Node::NullPtr;
525 }
526
538 void join_exclusive(Gen_Treap & t) noexcept
539 {
540 tree_root = join_exclusive(tree_root, t.tree_root);
541 t.tree_root = Node::NullPtr;
542 }
543
552 bool split_key(const Key & key, Gen_Treap & t1, Gen_Treap & t2)
553 {
554 return split_key_rec(tree_root, key, t1.getRoot(), t2.getRoot());
555 }
556
567 void split_key_dup(const Key & key, Gen_Treap & t1, Gen_Treap & t2)
568 {
569 split_key_dup_rec(tree_root, key, t1.getRoot(), t2.getRoot());
570 }
571
584 };
585
611 template <typename Key, class Compare = Aleph::less<Key>>
613 struct Treap : public Gen_Treap<TreapNode, Key, Compare>
614 {
616 using Base::Base;
617 };
618
619
645 template <typename Key, class Compare = Aleph::less<Key>>
647 struct Treap_Vtl : public Gen_Treap<TreapNodeVtl, Key, Compare>
648 {
650 using Base::Base;
651 };
652} // end namespace Aleph
653# endif // TPL_TREAP_H
C++20 concepts for constraining comparison functors.
Exception handling system with formatted messages for Aleph-w.
#define ah_bad_alloc_if(C)
Throws std::bad_alloc if condition holds.
Definition ah-errors.H:429
Standard functor implementations and comparison objects.
@ KEY
Definition btreepic.C:169
Inorder iterator on the nodes of a binary tree.
Treap - A randomized binary search tree using heap-ordered priorities.
Definition tpl_treap.H:150
Node * insert(Node *p) noexcept
Insert a node in a treap.
Definition tpl_treap.H:320
void set_seed(const unsigned long seed) noexcept
Set the random number generator seed.
Definition tpl_treap.H:173
Node * remove(const Key &key) noexcept
Remove a key from the tree.
Definition tpl_treap.H:381
bool verify() const noexcept
Return true if this is a consistent treap.
Definition tpl_treap.H:373
Gen_Treap(const unsigned long seed, const Compare &__cmp=Compare())
Initialize a treap with random seed and comparison criteria __cmp
Definition tpl_treap.H:191
void split_key_dup(const Key &key, Gen_Treap &t1, Gen_Treap &t2)
Split the tree according to a key that could be in the tree.
Definition tpl_treap.H:567
Node * search(const Key &key) const noexcept
Search a key in a treap.
Definition tpl_treap.H:222
NodeType< Key > Node
Definition tpl_treap.H:152
Node * insert_dup(Node *root, Node *p) noexcept
Definition tpl_treap.H:292
Node *& getRoot() noexcept
Return the tree's root.
Definition tpl_treap.H:214
void join_dup(Node *&t1, Node *t2) noexcept
Definition tpl_treap.H:462
void swap(Gen_Treap &tree) noexcept
Swap in constant time all the nodes of this with tree
Definition tpl_treap.H:176
void join(Gen_Treap &t, Gen_Treap &dup) noexcept
Join this with t filtering the duplicated keys.
Definition tpl_treap.H:507
void init(const unsigned int seed)
Definition tpl_treap.H:161
Compare & key_comp() noexcept
return the comparison criteria
Definition tpl_treap.H:184
Gen_Treap(const Compare &cmp=Compare())
Initialize a treap with random seed from system time and comparison criteria cmp
Definition tpl_treap.H:199
Node *& tree_root
Definition tpl_treap.H:157
Node * search_or_insert(Node *&root, Node *p) noexcept
Definition tpl_treap.H:263
Node * search_or_insert(Node *p) noexcept
Search or insert a key.
Definition tpl_treap.H:346
Node * insert_dup(Node *p) noexcept
Insert a node in the tree.
Definition tpl_treap.H:362
Compare & get_compare() noexcept
Definition tpl_treap.H:187
Node head
The type of node.
Definition tpl_treap.H:155
static Node * join_exclusive(Node *t1, Node *t2) noexcept
Definition tpl_treap.H:427
void join(Node *&t1, Node *t2, Node *&dup) noexcept
Definition tpl_treap.H:474
bool split_key(const Key &key, Gen_Treap &t1, Gen_Treap &t2)
Split the tree according to a key.
Definition tpl_treap.H:552
Node * remove(Node *&root, const Key &key) noexcept
Definition tpl_treap.H:444
void join_dup(Gen_Treap &t) noexcept
Join this with t independently of the presence of duplicated keys.
Definition tpl_treap.H:521
gsl_rng * gsl_rng_object() noexcept
Get a pointer to gsl random number generator.
Definition tpl_treap.H:211
void join_exclusive(Gen_Treap &t) noexcept
Join exclusive of this with t
Definition tpl_treap.H:538
Node * insert(Node *root, Node *p) noexcept
Definition tpl_treap.H:229
Strict weak ordering constraint for BST comparators.
Definition ah-concepts.H:84
__gmp_expr< T, __gmp_binary_expr< __gmp_expr< T, U >, unsigned long int, __gmp_root_function > > root(const __gmp_expr< T, U > &expr, unsigned long int l)
Definition gmpfrxx.h:4060
Node * rotate_to_left(Node *p) noexcept
Rotate to the left the tree with root p
Node * rotate_to_right(Node *p) noexcept
Rotate to the right the tree with root p
bool split_key_rec(Node *&root, const typename Node::key_type &key, Node *&ts, Node *&tg, const Compare &cmp=Compare()) noexcept
Split recursively according to a key.
void split_key_dup_rec(Node *&root, const typename Node::key_type &key, Node *&ts, Node *&tg, const Compare &cmp=Compare()) noexcept
Split a tree according to a key value.
Node * searchInBinTree(Node *root, const typename Node::key_type &key, const Compare &cmp=Compare()) noexcept
Search a key in a binary search tree.
unsigned long & PRIO(Node *p) noexcept
Access the priority of a treap node.
Definition treapNode.H:120
Main namespace for Aleph-w library functions.
Definition ah-arena.H:89
and
Check uniqueness with explicit hash + equality functors.
bool is_treap(Node *root) noexcept
Validate that a tree satisfies treap (heap) property.
Definition treapNode.H:144
Divide_Conquer_DP_Result< Cost > divide_and_conquer_partition_dp(const size_t groups, const size_t n, Transition_Cost_Fn transition_cost, const Cost inf=dp_optimization_detail::default_inf< Cost >())
Optimize partition DP using divide-and-conquer optimization.
const long Min_Priority
Minimum priority value.
Definition treapNode.H:78
static std::atomic< bool > init
Definition hash-fct.C:53
Iterator on nodes of the tree.
Definition tpl_treap.H:579
Iterator() noexcept=default
Default constructor creates an "end" iterator.
Treap (a special type of randomized binary search tree) using nodes with virtual destructors.
Definition tpl_treap.H:648
Treap (a special type of randomized binary search tree) using nodes without virtual destructor.
Definition tpl_treap.H:614
#define RLINK(i, n)
#define LLINK(i, n)
ValueArg< size_t > seed
Definition testHash.C:48
Utility functions for binary tree operations.
Binary tree operations (split, join, rotate).
Treap node definition with BST key and heap priority.
DynList< int > l