Aleph-w 3.0
A C++ Library for Data Structures and Algorithms
Loading...
Searching...
No Matches
sort_utils.cc
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
38#include <gtest/gtest.h>
39
40#include <tpl_sort_utils.H>
41#include <tpl_dynArray.H>
42#include <tpl_array.H>
43#include <tpl_dynList.H>
44#include <tpl_dynDlist.H>
45#include <tpl_dnode.H>
46
47using namespace Aleph;
48using namespace std;
49
50namespace {
51
52static DynArray<int> make_dynarray(std::initializer_list<int> xs)
53{
55 a.reserve(xs.size());
56 size_t i = 0;
57 for (const int x : xs)
58 a(i++) = x;
59 return a;
60}
61
62static DynList<int> make_dynlist(std::initializer_list<int> xs)
63{
65 for (int x : xs)
66 l.append(x);
67 return l;
68}
69
70static DynDlist<int> make_dyndlist(std::initializer_list<int> xs)
71{
73 for (int x : xs)
74 l.append(x);
75 return l;
76}
77
78static Dnode<int> make_dnode_list(std::initializer_list<int> xs)
79{
81 for (int x : xs)
82 h.append(new Dnode<int>(x));
83 return h;
84}
85
86static void delete_all_nodes(Dnode<int> & h)
87{
88 while (not h.is_empty())
89 delete h.remove_first_ne();
90}
91
93{
94 DynList<int> l = make_dynlist({1, 1, 2, 2, 3});
98}
99
101{
102 DynList<int> l = make_dynlist({1, 3, 2, 4});
104 auto inv = search_inversion(l);
105 EXPECT_FALSE(inv.first);
106 EXPECT_EQ(inv.second, 2u);
107}
108
110{
111 DynList<int> l = make_dynlist({5, 4, 4, 2, 1});
114}
115
117{
118 int a0[1] = {0};
119 selection_sort(a0, 0);
120 selection_sort(a0, 1);
121 EXPECT_EQ(a0[0], 0);
122}
123
125{
126 int a[] = {3, 1, 2, 1, 0};
127 selection_sort(a, sizeof(a) / sizeof(a[0]));
128 EXPECT_TRUE(std::is_sorted(std::begin(a), std::end(a)));
129}
130
132{
133 auto a = make_dynarray({10, 9, 3, 2, 1, 8, 7});
134 // sort only [2..4] (3,2,1)
135 insertion_sort(a, 2, 4);
136 EXPECT_EQ(a(0), 10);
137 EXPECT_EQ(a(1), 9);
138 EXPECT_EQ(a(2), 1);
139 EXPECT_EQ(a(3), 2);
140 EXPECT_EQ(a(4), 3);
141 EXPECT_EQ(a(5), 8);
142 EXPECT_EQ(a(6), 7);
143}
144
146{
147 auto a = make_dynarray({3, 1, 2, 1, 0});
149 for (size_t i = 1; i < a.size(); ++i)
150 ASSERT_LE(a(i - 1), a(i));
151}
152
154{
155 auto a = make_dynarray({3, 1, 2, 1, 0});
157 for (size_t i = 1; i < a.size(); ++i)
158 ASSERT_GE(a(i - 1), a(i));
159}
160
162{
163 auto a = make_dynarray({3, 1, 2, 1, 0});
164 bubble_sort(a);
165 for (size_t i = 1; i < a.size(); ++i)
166 ASSERT_LE(a(i - 1), a(i));
167}
168
170{
171 auto a = make_dynarray({0, 0, 1, 1, 2, 2});
172 bubble_sort(a);
173 for (size_t i = 1; i < a.size(); ++i)
174 ASSERT_LE(a(i - 1), a(i));
175 EXPECT_EQ(a(0), 0);
176 EXPECT_EQ(a(5), 2);
177}
178
179static bool is_min_heap(const DynArray<int> & a, size_t n)
180{
181 if (n <= 1)
182 return true;
183
184 for (size_t child = 2; child <= n; ++child)
185 {
186 size_t parent = child / 2;
187 if (a(parent - 1) > a(child - 1))
188 return false;
189 }
190 return true;
191}
192
194{
195 auto a = make_dynarray({5, 99, 0, 99, 99, 3, 99});
196 // l=0 => 5, m=3 => 99, r=6 => 99 => median is 99 => either m or r
197 long p = select_pivot_op<int>(a, 0, 6);
198 EXPECT_TRUE(p == 3 || p == 6);
199
200 auto b = make_dynarray({10, 99, 5, 99, 99, 99, 0});
201 // l=0 => 10, m=3 => 99, r=6 => 0 => median is 10 => l
202 EXPECT_EQ(select_pivot_op<int>(b, 0, 6), 0);
203
204 auto c = make_dynarray({0, 99, 99, 5, 99, 99, 10});
205 // l=0 => 0, m=3 => 5, r=6 => 10 => median is 5 => m
206 EXPECT_EQ(select_pivot_op<int>(c, 0, 6), 3);
207}
208
210{
211 Array<int> a;
212 for (int x : {5, 4, 3, 2, 1, 0})
213 a.append(x);
214
215 // r - l <= 5 => returns r
216 EXPECT_EQ(select_pivot_op<int>(a, 0, 5), 5);
217}
218
220{
221 auto a = make_dynarray({4, 1, 3, 2, 0, 2});
222 std::vector<int> before;
223 before.reserve(a.size());
224 for (size_t i = 0; i < a.size(); ++i)
225 before.push_back(a(i));
226
227 long p = partition_op<int>(a, 0, static_cast<long>(a.size() - 1));
228 ASSERT_GE(p, 0);
229 ASSERT_LT(static_cast<size_t>(p), a.size());
230
231 const int pivot = a(p);
232 for (long i = 0; i < p; ++i)
234 for (long i = p + 1; i < static_cast<long>(a.size()); ++i)
236
237 std::vector<int> after;
238 after.reserve(a.size());
239 for (size_t i = 0; i < a.size(); ++i)
240 after.push_back(a(i));
241 std::sort(before.begin(), before.end());
242 std::sort(after.begin(), after.end());
244}
245
247{
248 Array<int> a;
249 for (int x : {4, 1, 3, 2, 0, 2})
250 a.append(x);
251
252 std::vector<int> before;
253 before.reserve(a.size());
254 for (size_t i = 0; i < a.size(); ++i)
255 before.push_back(a(i));
256
257 long p = partition_op<int>(a, 0, static_cast<long>(a.size() - 1));
258 ASSERT_GE(p, 0);
259 ASSERT_LT(static_cast<size_t>(p), a.size());
260
261 const int pivot = a(p);
262 for (long i = 0; i < p; ++i)
264 for (long i = p + 1; i < static_cast<long>(a.size()); ++i)
266
267 std::vector<int> after;
268 after.reserve(a.size());
269 for (size_t i = 0; i < a.size(); ++i)
270 after.push_back(a(i));
271 std::sort(before.begin(), before.end());
272 std::sort(after.begin(), after.end());
274}
275
277{
278 {
279 auto a = make_dynarray({4, 1, 3, 2, 0, 2});
280 auto expected = std::vector<int>{4, 1, 3, 2, 0, 2};
281 std::sort(expected.begin(), expected.end());
285 }
286
287 {
288 Array<int> a;
289 for (int x : {4, 1, 3, 2, 0, 2})
290 a.append(x);
291 auto expected = std::vector<int>{4, 1, 3, 2, 0, 2};
292 std::sort(expected.begin(), expected.end());
296 }
297}
298
300{
301 EXPECT_EQ(back_index(10), 9);
302
304 EXPECT_TRUE(nc(2, 1));
305 EXPECT_FALSE(nc(1, 2));
306}
307
309{
310 int a[] = {4, 1, 3, 2, 0, 2};
312 int p = select_pivot<int, Aleph::less<int>>(a, 0, 5, cmp);
313 EXPECT_GE(p, 0);
314 EXPECT_LE(p, 5);
315
316 int q = partition<int, Aleph::less<int>>(a, 0, 5, cmp);
317 EXPECT_GE(q, 0);
318 EXPECT_LE(q, 5);
319}
320
322{
323 // [0..2] and [3..5] are already sorted
324 int a[] = {0, 2, 4, 1, 3, 5};
325 merge(a, 0, 2, 5, Aleph::less<int>());
326 EXPECT_TRUE(std::is_sorted(std::begin(a), std::end(a)));
327}
328
330{
331 FixedStack<int> st(10);
332 push2(st, 1, 2);
333 EXPECT_EQ(st.pop(), 1);
334 EXPECT_EQ(st.pop(), 2);
335 EXPECT_TRUE(st.is_empty());
336}
337
339{
340 int a[] = {5, 4, 3, 2, 1, 0, 0, 9};
341 quicksort_no_tail(a, 0, static_cast<int>((sizeof(a) / sizeof(a[0])) - 1));
342 EXPECT_TRUE(std::is_sorted(std::begin(a), std::end(a)));
343}
344
346{
347 Snodenc<int> n1(1), n2(2);
349 EXPECT_TRUE(cmp(static_cast<Slinknc *>(&n1), static_cast<Slinknc *>(&n2)));
350 EXPECT_TRUE(cmp(static_cast<Slinknc *>(&n1), 5));
351}
352
354{
356 Dlink & base = static_cast<Dlink &>(h);
357
358 auto * n2 = new Dnode<int>(2);
359 auto * n0 = new Dnode<int>(0);
360 auto * n1 = new Dnode<int>(1);
361
363 Cmp cmp{Aleph::less<int>()};
364
365 insert_sorted<Cmp>(base, n2, cmp);
366 insert_sorted<Cmp>(base, n0, cmp);
367 insert_sorted<Cmp>(base, n1, cmp);
369
370 // list_insertion_sort on Dlink
371 Dnode<int> h2 = make_dnode_list({3, 1, 2, 0});
372 Dlink & base2 = static_cast<Dlink &>(h2);
375
376 delete_all_nodes(h);
377 delete_all_nodes(h2);
378}
379
381{
383 l.append(0);
384 l.append(2);
385
386 auto * node = new Snodenc<int>(1);
388 insert_sorted(l, static_cast<Slinknc *>(node), cmp);
390
391 DynList<int> l2;
392 for (int x : {3, 1, 2, 0})
393 l2.append(x);
395 static_cast<HTList &>(l2), cmp);
397}
398
400{
401 auto h = make_dnode_list({4, 1, 3, 2, 0, 2});
402 Dlink & base = static_cast<Dlink &>(h);
403
405 Cmp cmp{Aleph::less<int>()};
406
407 auto * found = dlink_random_search(base, 3, cmp);
408 ASSERT_NE(found, nullptr);
409 EXPECT_EQ(found->get_data(), 3);
410
411 auto * sel = dlink_random_select(base, 0, cmp);
412 ASSERT_NE(sel, nullptr);
413 EXPECT_EQ(static_cast<Dnode<int> *>(sel)->get_data(), 0);
414
415 delete_all_nodes(h);
416}
417
419{
420 const auto a = make_dynarray({0, 1, 1, 1, 2, 3});
421 EXPECT_EQ(binindex(a, 2), 4);
422}
423
425{
426 int a[] = {4, 1, 3, 2, 0, 2};
427 std::vector<int> expected(std::begin(a), std::end(a));
428 std::sort(expected.begin(), expected.end());
429
434}
435
437{
439
440 // sift_up: insert new element at end and bubble up
441 {
443 a.reserve(4);
444 a(0) = 1;
445 a(1) = 3;
446 a(2) = 5;
447 a(3) = 0;
450 }
451
452 // sift_down: restore heap after root replaced
453 {
455 a.reserve(4);
456 a(0) = 3;
457 a(1) = 1;
458 a(2) = 2;
459 a(3) = 0; // outside heap when n=3
462 }
463}
464
466{
467 int a[] = {5, 4, 3, 2, 1, 0, 0, 9};
468 mergesort(a, 0, static_cast<int>((sizeof(a) / sizeof(a[0])) - 1));
469 EXPECT_TRUE(std::is_sorted(std::begin(a), std::end(a)));
470}
471
473{
474 int a[] = {5, 4, 3, 2, 1, 0, 0, 9};
475 quicksort(a, 0, static_cast<int>((sizeof(a) / sizeof(a[0])) - 1));
476 EXPECT_TRUE(std::is_sorted(std::begin(a), std::end(a)));
477}
478
480{
481 int a[] = {5, 4, 3, 2, 1, 0, 0, 9};
482 quicksort_rec(a, 0, static_cast<int>((sizeof(a) / sizeof(a[0])) - 1));
483 EXPECT_TRUE(std::is_sorted(std::begin(a), std::end(a)));
484}
485
487{
488 int a[] = {5, 4, 3, 2, 1, 0, 0, 9};
489 quicksort_rec_min(a, 0, static_cast<int>((sizeof(a) / sizeof(a[0])) - 1));
490 EXPECT_TRUE(std::is_sorted(std::begin(a), std::end(a)));
491}
492
494{
495 int a[] = {9, 1, 8, 2, 7, 3, 6, 4, 5, 0};
496 quicksort_insertion(a, 0, static_cast<int>((sizeof(a) / sizeof(a[0])) - 1));
497 EXPECT_TRUE(std::is_sorted(std::begin(a), std::end(a)));
498
499 int b[] = {2, 1};
500 quicksort_insertion(b, 0, 1);
501 EXPECT_TRUE(std::is_sorted(std::begin(b), std::end(b)));
502}
503
504// Introsort tests - hybrid algorithm with O(n log n) guaranteed
506{
507 int a[] = {5, 4, 3, 2, 1, 0, 0, 9};
508 introsort(a, 0L, static_cast<long>((sizeof(a) / sizeof(a[0])) - 1));
509 EXPECT_TRUE(std::is_sorted(std::begin(a), std::end(a)));
510}
511
513{
514 int a[] = {9, 1, 8, 2, 7, 3, 6, 4, 5, 0};
515 introsort(a, sizeof(a) / sizeof(a[0]));
516 EXPECT_TRUE(std::is_sorted(std::begin(a), std::end(a)));
517}
518
520{
521 int a[] = {1, 2, 3, 4, 5, 6, 7, 8, 9};
522 introsort(a, 0L, 8L, std::greater<int>());
523 EXPECT_TRUE(std::is_sorted(std::begin(a), std::end(a), std::greater<int>()));
524}
525
527{
528 auto a = make_dynarray({4, 1, 3, 2, 0, 2});
529 introsort(a);
530 for (size_t i = 1; i < a.size(); ++i)
531 ASSERT_LE(a(i - 1), a(i));
532}
533
535{
536 // Empty array
537 int empty[] = {0};
538 introsort(empty, 0);
539 EXPECT_EQ(empty[0], 0);
540
541 // Single element
542 int single[] = {42};
543 introsort(single, 1);
544 EXPECT_EQ(single[0], 42);
545
546 // Empty DynArray
549}
550
552{
553 int a[] = {1, 2, 3, 4, 5, 6, 7, 8, 9, 10};
554 introsort(a, sizeof(a) / sizeof(a[0]));
555 EXPECT_TRUE(std::is_sorted(std::begin(a), std::end(a)));
556}
557
559{
560 int a[] = {10, 9, 8, 7, 6, 5, 4, 3, 2, 1};
561 introsort(a, sizeof(a) / sizeof(a[0]));
562 EXPECT_TRUE(std::is_sorted(std::begin(a), std::end(a)));
563}
564
566{
567 int a[] = {5, 5, 5, 5, 5, 5, 5, 5, 5, 5};
568 introsort(a, sizeof(a) / sizeof(a[0]));
569 EXPECT_TRUE(std::is_sorted(std::begin(a), std::end(a)));
570}
571
573{
574 // Create an array large enough that might trigger heapsort fallback
575 // This tests the depth limit mechanism
576 const size_t n = 10000;
577 std::vector<int> v(n);
578 for (size_t i = 0; i < n; ++i)
579 v[i] = static_cast<int>(n - i); // Reverse sorted (worst case for quicksort)
580
581 introsort(v.data(), n);
582 EXPECT_TRUE(std::is_sorted(v.begin(), v.end()));
583}
584
586{
587 // Test with larger DynArray
588 const size_t n = 5000;
590 a.reserve(n);
591 for (size_t i = 0; i < n; ++i)
592 a(i) = static_cast<int>(n - i); // Reverse sorted
593
594 introsort(a);
595 for (size_t i = 1; i < n; ++i)
596 ASSERT_LE(a(i - 1), a(i)) << "Failed at index " << i;
597}
598
599// Introsort with STL-style pointer interface (begin, end)
601{
602 int a[] = {9, 1, 8, 2, 7, 3, 6, 4, 5, 0};
603 introsort(a, a + 10); // STL-style: introsort(begin, end)
604 EXPECT_TRUE(std::is_sorted(std::begin(a), std::end(a)));
605}
606
608{
609 int a[] = {9, 1, 8, 2, 7, 3, 6, 4, 5, 0};
610 // Sort only middle portion [2, 7)
611 introsort(a + 2, a + 7);
612 // Elements 0,1 unchanged, 2-6 sorted, 7-9 unchanged
613 EXPECT_EQ(a[0], 9);
614 EXPECT_EQ(a[1], 1);
615 EXPECT_TRUE(std::is_sorted(a + 2, a + 7));
616 EXPECT_EQ(a[7], 4);
617}
618
620{
621 int a[] = {1, 2, 3, 4, 5, 6, 7, 8, 9};
622 introsort(a, a + 9, std::greater<int>());
623 EXPECT_TRUE(std::is_sorted(std::begin(a), std::end(a), std::greater<int>()));
624}
625
627{
628 int a[] = {42};
629 // Empty range - should not crash
630 introsort(a, a);
631 EXPECT_EQ(a[0], 42); // Unchanged
632}
633
634// Introsort for Array<T> container
636{
637 Array<int> arr;
638 arr.append(5);
639 arr.append(2);
640 arr.append(8);
641 arr.append(1);
642 arr.append(9);
643 arr.append(3);
644
645 introsort(arr);
646
647 for (size_t i = 1; i < arr.size(); ++i)
648 ASSERT_LE(arr(i - 1), arr(i));
649}
650
652{
653 Array<int> arr;
654 for (int i = 1; i <= 10; ++i)
655 arr.append(i);
656
657 introsort(arr, std::greater<int>());
658
659 for (size_t i = 1; i < arr.size(); ++i)
660 ASSERT_GE(arr(i - 1), arr(i)); // Descending order
661}
662
664{
665 Array<int> arr;
667 EXPECT_TRUE(arr.is_empty());
668}
669
671{
672 Array<int> arr;
673 arr.append(42);
674 introsort(arr);
675 EXPECT_EQ(arr.size(), 1u);
676 EXPECT_EQ(arr(0), 42);
677}
678
680{
681 const size_t n = 5000;
682 Array<int> arr(n);
683 for (size_t i = 0; i < n; ++i)
684 arr.append(static_cast<int>(n - i)); // Reverse sorted
685
686 introsort(arr);
687
688 for (size_t i = 1; i < n; ++i)
689 ASSERT_LE(arr(i - 1), arr(i)) << "Failed at index " << i;
690}
691
693{
694 auto a = make_dynarray({4, 1, 3, 2, 0, 2});
695 heapsort(a);
696 for (size_t i = 1; i < a.size(); ++i)
697 ASSERT_LE(a(i - 1), a(i));
698}
699
701{
702 auto a = make_dynarray({4, 1, 3, 2, 0, 2});
703 quicksort_op(a);
704 for (size_t i = 1; i < a.size(); ++i)
705 ASSERT_LE(a(i - 1), a(i));
706}
707
709{
713}
714
716{
717 auto a = make_dynarray({9, 1, 8, 2, 7, 3, 6, 4, 5, 0});
718 shellsort(a);
719 for (size_t i = 1; i < a.size(); ++i)
720 ASSERT_LE(a(i - 1), a(i));
721}
722
724{
725 auto a = make_dynarray({4, 1, 3, 2, 0, 2});
726 quicksort(a);
727 for (size_t i = 1; i < a.size(); ++i)
728 ASSERT_LE(a(i - 1), a(i));
729}
730
732{
733 auto a = make_dynarray({4, 1, 3, 2, 0, 2});
734 quicksort_rec(a, 0, static_cast<long>(a.size() - 1));
735 for (size_t i = 1; i < a.size(); ++i)
736 ASSERT_LE(a(i - 1), a(i));
737}
738
740{
741 DynList<int> l = make_dynlist({4, 1, 3, 2, 0, 2});
742 mergesort(l);
744}
745
747{
748 DynList<int> l = make_dynlist({9, 8, 7, 6, 5, 4, 3, 2, 1, 0});
751}
752
754{
755 DynList<int> l = make_dynlist({4, 1, 3, 2, 0, 2});
756 DynList<int> sorted = insertion_sort(std::move(l));
759}
760
762{
763 DynList<int> l = make_dynlist({4, 1, 3, 2, 0, 2});
764 DynList<int> sorted = mergesort(std::move(l));
767}
768
770{
771 DynList<int> l = make_dynlist({4, 1, 3, 2, 0, 2});
772 quicksort(l);
774 EXPECT_EQ(l.get_first(), 0);
775 EXPECT_EQ(l.get_last(), 4);
776}
777
779{
780 DynList<int> l1 = make_dynlist({0, 2, 4});
781 DynList<int> l2 = make_dynlist({1, 3, 5});
783
784 merge_lists(l1, l2, out, Aleph::less<int>());
785 EXPECT_TRUE(l1.is_empty());
786 EXPECT_TRUE(l2.is_empty());
788 EXPECT_EQ(out.size(), 6u);
789 EXPECT_EQ(out.get_first(), 0);
790 EXPECT_EQ(out.get_last(), 5);
791}
792
794{
795 auto l1 = make_dnode_list({0, 2, 4});
796 auto l2 = make_dnode_list({1, 3, 5});
798
799 merge_lists(l1, l2, out, Aleph::less<int>());
800
801 EXPECT_TRUE(l1.is_empty());
802 EXPECT_TRUE(l2.is_empty());
804
805 int expected = 0;
806 for (Dnode<int>::Iterator it(out); it.has_curr(); it.next_ne(), ++expected)
807 EXPECT_EQ(it.get_curr_ne()->get_data(), expected);
809
810 delete_all_nodes(out);
811}
812
814{
815 DynDlist<int> l = make_dyndlist({4, 1, 3, 2, 0, 2});
816 mergesort(l);
818}
819
821{
822 DynDlist<int> l = make_dyndlist({4, 1, 3, 2, 0, 2});
823 int * p = search_extreme(l);
824 ASSERT_NE(p, nullptr);
825 EXPECT_EQ(*p, 0);
826}
827
829{
830 DynDlist<int> l = make_dyndlist({4, 1, 3, 2, 0, 2});
831 int * p = random_select(l, 0);
832 ASSERT_NE(p, nullptr);
833 EXPECT_EQ(*p, 0);
834
835 p = random_select(l, 5);
836 ASSERT_NE(p, nullptr);
837 EXPECT_EQ(*p, 4);
838}
839
841{
842 DynDlist<int> l = make_dyndlist({4, 1, 3, 2, 0, 2});
843
844 int * p = random_search(l, 3);
845 ASSERT_NE(p, nullptr);
846 EXPECT_EQ(*p, 3);
847
848 p = random_search(l, 99);
849 EXPECT_EQ(p, nullptr);
850}
851
853{
854 auto h = make_dnode_list({4, 1, 3, 2, 0, 2});
855
856 auto * n0 = random_select<int>(h, 0);
857 ASSERT_NE(n0, nullptr);
858 EXPECT_EQ(n0->get_data(), 0);
859
860 auto * nmax = random_select<int>(h, 5);
861 ASSERT_NE(nmax, nullptr);
862 EXPECT_EQ(nmax->get_data(), 4);
863
864 auto * nfound = random_search<int>(h, 3);
865 ASSERT_NE(nfound, nullptr);
866 EXPECT_EQ(nfound->get_data(), 3);
867
868 auto * nmiss = random_search<int>(h, 99);
869 EXPECT_EQ(nmiss, nullptr);
870
871 delete_all_nodes(h);
872}
873
875{
876 DynList<int> l = make_dynlist({4, 1, 3, 2, 0, 2});
877 quicksort<int>(static_cast<HTList &>(l), Aleph::less<int>());
879}
880
882{
883 int a[] = {4, 1, 3, 2, 0, 2};
884 EXPECT_EQ(sequential_search(a, int{3}, 0, 5), 2);
885 EXPECT_EQ(sequential_search(a, int{99}, 0, 5), Not_Found);
886}
887
889{
890 auto a = make_dynarray({4, 1, 3, 2, 0, 2});
891 EXPECT_EQ(sequential_search(a, 3, 0, static_cast<int>(a.size() - 1)), 2);
892 EXPECT_EQ(sequential_search(a, 99, 0, static_cast<int>(a.size() - 1)), Not_Found);
893}
894
896{
897 DynList<int> l = make_dynlist({4, 1, 3, 2, 0, 2});
898 int * p = sequential_search(l, 3);
899 ASSERT_NE(p, nullptr);
900 EXPECT_EQ(*p, 3);
901
902 p = sequential_search(l, 99);
903 EXPECT_EQ(p, nullptr);
904}
905
907{
908 DynDlist<int> l = make_dyndlist({4, 1, 3, 2, 0, 2});
909 int * p = sequential_search(l, 3);
910 ASSERT_NE(p, nullptr);
911 EXPECT_EQ(*p, 3);
912 p = sequential_search(l, 99);
913 EXPECT_EQ(p, nullptr);
914}
915
917{
918 auto h = make_dnode_list({4, 1, 3, 2, 0, 2});
919
920 auto * n = sequential_search(h, 3);
921 ASSERT_NE(n, nullptr);
922 EXPECT_EQ(n->get_data(), 3);
923
924 n = sequential_search(h, 99);
925 EXPECT_EQ(n, nullptr);
926
927 delete_all_nodes(h);
928}
929
931{
932 auto h = make_dnode_list({4, 1, 3, 2, 0, 2});
934 ASSERT_NE(n, nullptr);
935 EXPECT_EQ(n->get_data(), 0);
936 delete_all_nodes(h);
937}
938
940{
941 int a[] = {4, 1, 3, 2, 0, 2};
942 EXPECT_EQ(search_min(a, 0, 5), 4);
943 EXPECT_EQ(search_max(a, 0, 5), 0);
944}
945
947{
948 auto a = make_dynarray({4, 1, 3, 2, 0, 2});
949 EXPECT_EQ(search_extreme(a, 0, static_cast<long>(a.size() - 1)), 4);
950 EXPECT_EQ(search_max(a, 0, static_cast<long>(a.size() - 1)), 0);
951}
952
954{
955 DynDlist<int> l = make_dyndlist({4, 1, 3, 2, 0, 2});
956 int * mn = search_min(l);
957 int * mx = search_max(l);
958 ASSERT_NE(mn, nullptr);
959 ASSERT_NE(mx, nullptr);
960 EXPECT_EQ(*mn, 0);
961 EXPECT_EQ(*mx, 4);
962}
963
965{
966 DynList<int> l = make_dynlist({4, 1, 3, 2, 0, 2});
967 int * mn = search_extreme(l);
969 ASSERT_NE(mn, nullptr);
970 ASSERT_NE(mx, nullptr);
971 EXPECT_EQ(*mn, 0);
972 EXPECT_EQ(*mx, 4);
973}
974
976{
977 DynList<int> l = make_dynlist({4, 1, 3, 2, 0, 2});
980 ASSERT_NE(mn, nullptr);
981 ASSERT_NE(mx, nullptr);
982 EXPECT_EQ(*mn, 0);
983 EXPECT_EQ(*mx, 4);
984}
985
987{
988 {
989 auto h = make_dnode_list({4, 1, 3, 2, 0, 2});
992 delete_all_nodes(h);
993 }
994
995 {
996 auto h = make_dnode_list({4, 1, 3, 2, 0, 2});
999 delete_all_nodes(h);
1000 }
1001
1002 {
1003 auto h = make_dnode_list({4, 1, 3, 2, 0, 2});
1004 quicksort(h);
1005 EXPECT_EQ(search_extreme<int>(h, Aleph::less<int>())->get_data(), 0);
1006 delete_all_nodes(h);
1007 }
1008
1009 {
1010 auto h = make_dnode_list({4, 1, 3, 2, 0, 2});
1011 mergesort(h);
1012 EXPECT_EQ(search_extreme<int>(h, Aleph::less<int>())->get_data(), 0);
1013 delete_all_nodes(h);
1014 }
1015}
1016
1018{
1019 auto h = make_dnode_list({4, 1, 3, 2, 0, 2});
1020 Dlink & base = static_cast<Dlink &>(h);
1021
1023 quicksort(base, Cmp(Aleph::less<int>()));
1024
1025 EXPECT_EQ(search_extreme<int>(h, Aleph::less<int>())->get_data(), 0);
1027
1028 delete_all_nodes(h);
1029}
1030
1032{
1033 auto a = make_dynarray({0, 1, 1, 1, 2, 3});
1034
1035 auto idxs = binary_search_dup(a, 1);
1036 ASSERT_EQ(idxs.size(), 3u);
1037 EXPECT_EQ(idxs.get_first(), 1u);
1038 EXPECT_EQ(idxs.get_last(), 3u);
1039
1040 int * p = bsearch(a, 1);
1041 ASSERT_NE(p, nullptr);
1042 EXPECT_EQ(*p, 1);
1043 EXPECT_EQ(bsearch(a, 99), nullptr);
1044}
1045
1047{
1048 {
1049 auto a = make_dynarray({1, 1, 1, 2, 3});
1050 auto idxs = binary_search_dup(a, 1);
1051 ASSERT_EQ(idxs.size(), 3u);
1052 EXPECT_EQ(idxs.get_first(), 0u);
1053 EXPECT_EQ(idxs.get_last(), 2u);
1054 }
1055
1056 {
1057 auto a = make_dynarray({0, 1, 2, 3, 3, 3});
1058 auto idxs = binary_search_dup(a, 3);
1059 ASSERT_EQ(idxs.size(), 3u);
1060 EXPECT_EQ(idxs.get_first(), 3u);
1061 EXPECT_EQ(idxs.get_last(), 5u);
1062 }
1063}
1064
1066{
1067 // Descending sorted with duplicates
1068 auto a = make_dynarray({5, 4, 3, 3, 3, 2, 1, 1, 0});
1070 ASSERT_EQ(idxs.size(), 3u);
1071 EXPECT_EQ(idxs.get_first(), 2u);
1072 EXPECT_EQ(idxs.get_last(), 4u);
1073
1075 ASSERT_EQ(idxs.size(), 2u);
1076 EXPECT_EQ(idxs.get_first(), 6u);
1077 EXPECT_EQ(idxs.get_last(), 7u);
1078}
1079
1081{
1082 auto a = make_dynarray({5, 4, 3, 3, 3, 2, 1, 1, 0});
1083 auto ps = bsearch_dup(a, 3, Aleph::greater<int>());
1084 ASSERT_EQ(ps.size(), 3u);
1085 for (auto p : ps)
1086 {
1087 ASSERT_NE(p, nullptr);
1088 EXPECT_EQ(*p, 3);
1089 }
1090}
1091
1093{
1094 auto a = make_dynarray({3, 1, 2, 1, 0});
1095
1096 auto idx = build_index(a);
1097 ASSERT_EQ(idx.size(), a.size());
1098 for (size_t i = 1; i < idx.size(); ++i)
1099 ASSERT_LE(a(idx(i - 1)), a(idx(i)));
1100
1101 auto ptrs = build_index_ptr(a);
1102 ASSERT_EQ(ptrs.size(), a.size());
1103 for (size_t i = 1; i < ptrs.size(); ++i)
1104 ASSERT_LE(*ptrs(i - 1), *ptrs(i));
1105}
1106
1108{
1109 Slinknc head;
1110 auto * n1 = new Snodenc<int>(4);
1111 auto * n2 = new Snodenc<int>(1);
1112 auto * n3 = new Snodenc<int>(3);
1113 auto * n4 = new Snodenc<int>(0);
1114 head.insert(n1);
1115 head.insert(n2);
1116 head.insert(n3);
1117 head.insert(n4);
1118
1119 auto found = sequential_search(head, 3);
1120 ASSERT_NE(found, nullptr);
1121 EXPECT_EQ(static_cast<Snodenc<int>*>(found)->get_data(), 3);
1122
1123 auto missing = sequential_search(head, 99);
1124 EXPECT_EQ(missing, nullptr);
1125
1127 ASSERT_NE(extreme_min, nullptr);
1128 EXPECT_EQ(static_cast<Snodenc<int>*>(extreme_min)->get_data(), 0);
1129
1130 while (not head.is_empty())
1131 delete static_cast<Snodenc<int>*>(head.remove_next());
1132}
1133
1135{
1136 Slinknc head;
1137 auto * n1 = new Snodenc<int>(2);
1138 auto * n2 = new Snodenc<int>(1);
1139 auto * n3 = new Snodenc<int>(0);
1140 head.insert(n1);
1141 head.insert(n2);
1142 head.insert(n3);
1143
1144 auto * found = sequential_search<int>(head, 1);
1145 ASSERT_NE(found, nullptr);
1146 EXPECT_EQ(found->to_data<int>(), 1);
1147
1148 auto * missing = sequential_search<int>(head, 99);
1149 EXPECT_EQ(missing, nullptr);
1150
1151 while (not head.is_empty())
1152 delete static_cast<Snodenc<int>*>(head.remove_next());
1153}
1154
1156{
1157 auto h = make_dnode_list({3, 1, 2, 0});
1158 Dlink & base = static_cast<Dlink &>(h);
1159
1160 auto * found = sequential_search<int>(base, 2);
1161 ASSERT_NE(found, nullptr);
1162 EXPECT_EQ(static_cast<Dnode<int>*>(found)->get_data(), 2);
1163
1166 ASSERT_NE(mn, nullptr);
1167 EXPECT_EQ(mn->get_data(), 0);
1168
1169 delete_all_nodes(h);
1170}
1171
1173{
1174 int a[] = {4, 1, 3, 2, 0, 2};
1175 int idx = random_search(a, 3, 0, 5);
1176 ASSERT_NE(idx, Not_Found);
1177 EXPECT_EQ(a[idx], 3);
1178 EXPECT_EQ(random_search(a, 99, 0, 5), Not_Found);
1179
1180 auto d = make_dynarray({4, 1, 3, 2, 0, 2});
1181 idx = random_search(d, 3, 0, static_cast<long>(d.size() - 1));
1182 ASSERT_NE(idx, Not_Found);
1183 EXPECT_EQ(d(idx), 3);
1184 EXPECT_EQ(random_search(d, 99, 0, static_cast<long>(d.size() - 1)), Not_Found);
1185}
1186
1188{
1189 Array<int> a;
1190 for (int x : {4, 1, 3, 2, 0, 2})
1191 a.append(x);
1192
1193 EXPECT_EQ(random_select(a, 0), 0);
1194 EXPECT_EQ(random_select(a, 5), 4);
1195}
1196
1198{
1199 {
1200 DynArray<int> a;
1201 EXPECT_THROW(random_select(a, 0), std::out_of_range);
1202 }
1203
1204 {
1205 auto a = make_dynarray({4, 1, 3});
1206 EXPECT_THROW(random_select(a, 3), std::out_of_range);
1207 }
1208
1209 {
1210 Array<int> a;
1211 a.append(1);
1212 EXPECT_THROW(random_select(a, 1), std::out_of_range);
1213 }
1214
1215 {
1216 int b[] = {4, 1, 3};
1217 using Cmp = Aleph::less<int>;
1218 auto fn = static_cast<const int & (*)(int *, const long, const long, const Cmp &)>(
1220 EXPECT_THROW(fn(b, 3, 3, Cmp()), std::out_of_range);
1221 }
1222
1223 {
1224 Dnode<int> h;
1225 EXPECT_EQ(random_select<int>(h, 0), nullptr);
1226 EXPECT_EQ(random_select<int>(h, 1), nullptr);
1227 }
1228
1229 {
1231 EXPECT_EQ(random_select(l, 0), nullptr);
1232 EXPECT_EQ(random_select(l, 1), nullptr);
1233 }
1234
1235 {
1236 auto h = make_dnode_list({4, 1});
1237 EXPECT_THROW(random_select<int>(h, 2), std::out_of_range);
1238 delete_all_nodes(h);
1239 }
1240
1241 {
1242 auto l = make_dyndlist({4, 1});
1243 EXPECT_THROW(random_select(l, 2), std::out_of_range);
1244 }
1245}
1246
1248{
1249 auto a = make_dynarray({0, 2, 4, 6});
1250
1251 EXPECT_EQ(binary_search(a, 0), 0);
1252 EXPECT_EQ(binary_search(a, 6), 3);
1253
1254 // insertion points
1255 EXPECT_EQ(binary_search(a, 1), 1);
1256 EXPECT_EQ(binary_search(a, 5), 3);
1257 EXPECT_EQ(binary_search(a, 7), 4);
1258}
1259
1261{
1262 int a[] = {0, 2, 4, 6};
1263 EXPECT_EQ(binary_search(a, 0, 0, 3), 0);
1264 EXPECT_EQ(binary_search(a, 6, 0, 3), 3);
1265 EXPECT_EQ(binary_search(a, 1, 0, 3), 1);
1266 EXPECT_EQ(binary_search(a, 5, 0, 3), 3);
1267 EXPECT_EQ(binary_search(a, 7, 0, 3), 4);
1268}
1269
1271{
1272 int a[] = {0, 2, 4, 6};
1273 EXPECT_EQ(binary_search_rec(a, 0, 0, 3), 0);
1274 EXPECT_EQ(binary_search_rec(a, 6, 0, 3), 3);
1275 EXPECT_EQ(binary_search_rec(a, 1, 0, 3), 1);
1276 EXPECT_EQ(binary_search_rec(a, 5, 0, 3), 3);
1277 EXPECT_EQ(binary_search_rec(a, 7, 0, 3), 4);
1278}
1279
1281{
1282 auto a = make_dynarray({4, 1, 3, 2, 0, 2});
1283 EXPECT_EQ(random_select(a, 0), 0);
1284 EXPECT_EQ(random_select(a, 5), 4);
1285
1286 int b[] = {4, 1, 3, 2, 0, 2};
1287 using Cmp = Aleph::less<int>;
1288 auto fn = static_cast<const int & (*)(int *, const long, const long, const Cmp &)>(
1290 EXPECT_EQ(fn(b, 0, 6, Cmp()), 0);
1291 EXPECT_EQ(fn(b, 5, 6, Cmp()), 4);
1292}
1293
1295{
1296 auto a = make_dynarray({0, 2, 4, 6});
1297 DynArray<int *> idx;
1298 idx.reserve(a.size());
1299 for (size_t i = 0; i < a.size(); ++i)
1300 idx(i) = &a(i);
1301
1302 // already sorted pointers by value
1303 EXPECT_EQ(binary_search(idx, 0), 0);
1304 EXPECT_EQ(binary_search(idx, 6), 3);
1305 EXPECT_EQ(binary_search(idx, 1), 1);
1306 EXPECT_EQ(binary_search(idx, 7), 4);
1307}
1308
1310{
1311 auto a = make_dynarray({0, 1, 1, 1, 2, 3});
1312 auto ptrs = bsearch_dup(a, 1);
1313 ASSERT_EQ(ptrs.size(), 3u);
1314 for (auto p : ptrs)
1315 ASSERT_NE(p, nullptr);
1316
1317 auto idxs = binindex_dup(a, 1);
1318 ASSERT_EQ(idxs.size(), 3u);
1319 EXPECT_EQ(idxs.get_first(), 1);
1320 EXPECT_EQ(idxs.get_last(), 3);
1321}
1322
1324{
1325 auto a = make_dynarray({5, 4, 3, 3, 3, 2, 1, 1, 0});
1327 ptrs.reserve(a.size());
1328 for (size_t i = 0; i < a.size(); ++i)
1329 ptrs(i) = &a(i);
1330
1331 auto dup = bsearch_dup(ptrs, 3, Aleph::greater<int>());
1332 ASSERT_EQ(dup.size(), 3u);
1333 for (auto p : dup)
1334 {
1335 ASSERT_NE(p, nullptr);
1336 EXPECT_EQ(*p, 3);
1337 }
1338}
1339
1341{
1342 auto a = make_dynarray({5, 4, 3, 3, 3, 2, 1, 1, 0});
1344 ptrs.reserve(a.size());
1345 for (size_t i = 0; i < a.size(); ++i)
1346 ptrs(i) = &a(i);
1347
1349 ASSERT_EQ(idxs.size(), 3u);
1350 EXPECT_EQ(idxs.get_first(), 2);
1351 EXPECT_EQ(idxs.get_last(), 4);
1352}
1353
1355{
1356 auto a = make_dynarray({0, 1, 1, 1, 2, 3});
1358 ptrs.reserve(a.size());
1359 for (size_t i = 0; i < a.size(); ++i)
1360 ptrs(i) = &a(i);
1361
1362 auto found = bsearch(ptrs, 1);
1363 ASSERT_NE(found, nullptr);
1364 EXPECT_EQ(*found, 1);
1365
1366 auto dup = bsearch_dup(ptrs, 1);
1367 ASSERT_EQ(dup.size(), 3u);
1368 for (auto p : dup)
1369 {
1370 ASSERT_NE(p, nullptr);
1371 EXPECT_EQ(*p, 1);
1372 }
1373}
1374
1376{
1377 auto a = make_dynarray({0, 1, 1, 1, 2, 3});
1379 ptrs.reserve(a.size());
1380 for (size_t i = 0; i < a.size(); ++i)
1381 ptrs(i) = &a(i);
1382
1383 auto idxs = binindex_dup(ptrs, 1);
1384 ASSERT_EQ(idxs.size(), 3u);
1385 EXPECT_EQ(idxs.get_first(), 1);
1386 EXPECT_EQ(idxs.get_last(), 3);
1387}
1388
1390{
1391 auto a = make_dynarray({5, 4, 3, 2, 1, 0});
1393 ptrs.reserve(a.size());
1394 for (size_t i = 0; i < a.size(); ++i)
1395 ptrs(i) = &a(i);
1396
1397 // The container is sorted in descending order, so we must use greater<int>
1401}
1402
1404{
1405 auto a = make_dynarray({0, 1, 2, 3, 4, 5});
1407 ptrs.reserve(a.size());
1408 for (size_t i = 0; i < a.size(); ++i)
1409 ptrs(i) = &a(i);
1410
1411 // search only in [2..4] => values {2,3,4}
1412 EXPECT_EQ(binary_search(ptrs, 3, 2, 4), 3);
1413
1414 // insertion points within the restricted range
1415 EXPECT_EQ(binary_search(ptrs, 1, 2, 4), 2);
1416 EXPECT_EQ(binary_search(ptrs, 5, 2, 4), 5);
1417}
1418
1420{
1421 auto a = make_dynarray({5, 4, 3, 2, 1, 0});
1423 ptrs.reserve(a.size());
1424 for (size_t i = 0; i < a.size(); ++i)
1425 ptrs(i) = &a(i);
1426
1427 // search only in [1..3] => values {4,3,2} under greater<int>
1429
1430 // insertion points within the restricted range for descending order
1431 // 5 would be inserted before 4 => at l
1433 // 0 would be inserted after 2 => at r+1
1435}
1436
1437} // namespace
static bool is_min_heap(const std::vector< int > &v)
long double h
Definition btreepic.C:154
Simple dynamic array with automatic resizing and functional operations.
Definition tpl_array.H:138
constexpr size_t size() const noexcept
Return the number of elements stored in the stack.
Definition tpl_array.H:333
constexpr bool is_empty() const noexcept
Return true if stack is empty.
Definition tpl_array.H:330
T & append(const T &data)
Append a copy of data
Definition tpl_array.H:239
Iterator on a list of Dnode objects.
Definition tpl_dnode.H:261
Node belonging to a double circular linked list with header node.
Definition tpl_dnode.H:106
Dnode< T > * remove_first_ne() noexcept
Remove the first node and return its address.
Definition tpl_dnode.H:152
size_t size() const noexcept
Return the current dimension of array.
bool is_empty() const noexcept
Return true if the array is empty.
void reserve(const size_t l, const size_t r)
Allocate a range of entries.
Dynamic doubly linked list with O(1) size and bidirectional access.
Dynamic singly linked list with functional programming support.
Definition htlist.H:1423
T & append(const T &item)
Append a new item by copy.
Definition htlist.H:1562
T & get_last() const
Return the last item of the list.
Definition htlist.H:1663
T & get_first() const
Return the first item of the list.
Definition htlist.H:1675
Fixed length stack.
Single linked list of nodes.
Definition htlist.H:507
constexpr bool is_empty() const noexcept
Return true if list is empty.
Definition htlist.H:523
size_t size() const noexcept
Count the number of elements of the list.
Definition htlist.H:1319
Comparator wrapper that inverts the comparison order.
Link of a single linked list non-circular and without header node.
Definition htlist.H:100
constexpr bool is_empty() const noexcept
Return true if this is empty.
Definition htlist.H:108
Slinknc * remove_next() noexcept
Remove for linked list the node pointed by this
Definition htlist.H:177
void insert(Slinknc *p) noexcept
Insert p after this
Definition htlist.H:159
Node belonging to a single non-circular linked list without header node.
Definition htlist.H:328
iterator end() noexcept
Return an STL-compatible end iterator.
iterator begin() noexcept
Return an STL-compatible iterator to the first element.
#define TEST(name)
int cmp(const __gmp_expr< T, U > &expr1, const __gmp_expr< V, W > &expr2)
Definition gmpfrxx.h:4118
Main namespace for Aleph-w library functions.
Definition ah-arena.H:89
DynList< size_t > binary_search_dup(const C< T > &a, const T &x, const Compare &cmp=Compare())
long search_min(T *a, const long l, const long r, const Compare &cmp=Compare())
Returns the smallest element of the array a between l and r.
bool is_sorted(const Container< T > &cont, const Compare &cmp=Compare())
Check if a container is sorted in ascending order.
std::pair< bool, size_t > search_inversion(const Container< T > &cont, const Compare &cmp=Compare())
Find the first inversion in a container.
Dnode< T > * dlink_random_search(Dlink &list, const T &x, const Compare &cmp=Compare())
Random search for an element in a dlink list.
DynArray< T * > build_index_ptr(const C< T > &a, const Compare &cmp=Compare())
Builds and returns an array of pointers to the elements of container a sorted according to the compar...
void quicksort_no_tail(T *a, long l, long r, const Compare &cmp=Compare())
long random_search(T *a, const T &x, const long l, const long r, const Compare &cmp=Compare())
Random search for an element in an array.
const int Not_Found
Return value for search functions when element is not found.
std::pair< bool, size_t > test_sorted(const Container< T > &cont, const Compare &cmp=Compare())
Test if a container is sorted, returning the inversion position.
long search_max(T *a, const long l, const long r, const Compare &cmp=Compare())
Returns the maximum element of the array a between l and r.
void mergeinsertsort(Tlist< T > &list, const Compare &cmp=Compare(), const size_t lsz=Aleph::Insertion_Threshold)
Sort a list by mergesort combined with the insert method.
void insert_sorted(Dlink &list, Dlink *p, const Compare &cmp)
Inserts a node orderly into a doubly linked list.
Dlink * dlink_random_select(Dlink &list, const size_t i, const Compare &cmp=Compare())
Random selection of the ith element from a list based about Dlink.
void heapsort(T *array, const size_t n, const Compare &cmp=Compare())
Sort an array using the heapsort algorithm.
void mergesort(T *a, const long l, const long r, std::vector< T > &buf, Compare cmp)
T * bsearch(const C< T > &a, const T &x, const Compare &cmp=Compare())
DynArray< size_t > build_index(const C< T > &a, const Compare &cmp=Compare())
Build an index array for indirect sorting.
static const T & __random_select(T *a, const long i, const long l, const long r, const Compare &cmp)
const T & random_select(DynArray< T > &a, const long i, const Compare &cmp=Compare())
static long back_index(const long i) noexcept
void bubble_sort(DynArray< T > &a, const Compare &cmp=Compare())
Sort a dynamic array using bubble sort.
DynList< T * > bsearch_dup(const C< T > &a, const T &x, const Compare &cmp=Compare())
void quicksort(T *a, const long l, const long r, const Compare &cmp=Compare())
Sort an array using iterative quicksort with optimizations.
void insertion_sort(T *a, const long l, const long r, const Compare &cmp=Compare()) noexcept(noexcept(cmp(a[0], a[0])) &&std::is_nothrow_move_assignable_v< T >)
Sort an array using insertion sort.
void shellsort(DynArray< T > &a, const Compare &cmp=Compare())
Sort a dynamic array using Shell sort.
Itor3 merge(Itor1 source1Beg, Itor1 source1End, Itor2 source2Beg, Itor2 source2End, Itor3 destBeg)
Merge two sorted ranges.
Definition ahAlgo.H:1410
void quicksort_rec_min(T *a, const long l, const long r, const Compare &cmp=Compare())
Sorts an array according to the quicksort method with minimum space consumption.
long sequential_search(T *a, const T &x, const long l, const long r, Equal eq=Equal())
Linear search for an element in an array.
Link * search_extreme(const Link &list, const Compare &cmp)
Find the extreme (minimum or maximum) element in a linked list.
bool binary_search(Itor beg, Itor end, const T &value)
Binary search for a value.
Definition ahAlgo.H:1284
void quicksort_rec(T *a, const long l, const long r, const Compare &cmp=Compare())
Sorts an array using the quicksort method.
DynList< long > binindex_dup(const C< T > &a, const T &x, const Compare &cmp=Compare())
Returns the indices of all occurrences of a value in a sorted container.
bool is_inversely_sorted(const Container< T > &cont, const Compare &cmp=Compare())
Check if a container is sorted in descending order.
void selection_sort(T *a, const size_t n, const Compare &cmp=Compare()) noexcept(noexcept(cmp(a[0], a[0])) &&std::is_nothrow_swappable_v< T >)
Sort an array using the selection sort algorithm.
void introsort(T *a, const long l, const long r, const Compare &cmp=Compare())
Sort an array using introsort (introspective sort).
long binindex(const C< T > &a, const T &x, const Compare &cmp=Compare())
Returns the index where a value appears (or should be inserted) in a sorted container.
void quicksort_insertion(T *a, const long l, const long r, const Compare &cmp=Compare())
Sorts an array by the improved quicksort method.
long binary_search_rec(T *a, const T &x, const long l, const long r, const Compare &cmp=Compare())
Recursive binary search on an ordered array.
void merge_lists(Tlist &l1, Tlist &l2, Tlist &result, const Compare &cmp=Compare())
Merge two sorted lists into a single sorted list.
DynList< T > maps(const C &c, Op op)
Classic map operation.
void push2(Stack &stack, const A &a, const B &b)
void quicksort_op(C< T > &a, const Compare &cmp=Compare(), const size_t threshold=Quicksort_Threshold)
Optimized quicksort for containers using operator().
STL namespace.
Dynamic array container with automatic resizing.
Doubly linked list node with typed data.
Lazy and scalable dynamic array implementation.
Dynamic doubly linked list implementation.
Alias for htlist.H (DynList implementation).
Comprehensive sorting algorithms and search utilities for Aleph-w.
DynList< int > l