Aleph-w 3.0
A C++ Library for Data Structures and Algorithms
Loading...
Searching...
No Matches
segment_tree_example.cc
Go to the documentation of this file.
1/*
2 Aleph_w
3
4 Data structures & Algorithms
5 version 2.0.0b
6 https://github.com/lrleon/Aleph-w
7
8 This file is part of Aleph-w library
9
10 Copyright (c) 2002-2026 Leandro Rabindranath Leon
11
12 Permission is hereby granted, free of charge, to any person obtaining a copy
13 of this software and associated documentation files (the "Software"), to deal
14 in the Software without restriction, including without limitation the rights
15 to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
16 copies of the Software, and to permit persons to whom the Software is
17 furnished to do so, subject to the following conditions:
18
19 The above copyright notice and this permission notice shall be included in all
20 copies or substantial portions of the Software.
21
22 THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
23 IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
24 FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
25 AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
26 LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
27 OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
28 SOFTWARE.
29*/
30
62# include <tpl_segment_tree.H>
63# include <tpl_sparse_table.H>
64# include <iostream>
65# include <iomanip>
66
67using namespace Aleph;
68
70{
71 std::cout << "=== SCENARIO 1: El Arbol del Tiempo ===\n\n";
72 std::cout << "A historian tracks the oldest artifact per century.\n";
73 std::cout << "Index i represents century (i+1).\n\n";
74
75 // Oldest artifact year per century (lower = older)
76 // Centuries 1-10
78 -3000, // century 1: oldest artifact from 3000 BC
79 -2500, // century 2
80 -1800, // century 3
81 -1200, // century 4
82 -800, // century 5
83 -500, // century 6
84 -200, // century 7
85 100, // century 8
86 400, // century 9
87 700 // century 10
88 };
89
90 std::cout << "Initial oldest dates per century (negative = BC):\n";
91 for (size_t i = 0; i < timeline.size(); ++i)
92 std::cout << " Century " << (i + 1) << ": " << timeline.get(i) << "\n";
93
94 std::cout << "\nOldest artifact in centuries 3-7: "
95 << timeline.query(2, 6) << "\n";
96 std::cout << "Oldest artifact in centuries 1-5: "
97 << timeline.query(0, 4) << "\n";
98
99 // New archaeological discovery!
100 std::cout << "\nNew discovery: artifact from -2000 found in century 5!\n";
101 timeline.set(4, -2000);
102
103 std::cout << "Oldest artifact in centuries 3-7 (updated): "
104 << timeline.query(2, 6) << "\n";
105
106 std::cout << "\n";
107}
108
110{
111 std::cout << "=== SCENARIO 2: Ajustes Salariales ===\n\n";
112 std::cout << "HR system: 8 departments, salary adjustments and payroll queries.\n\n";
113
114 // Initial salaries per department (in thousands)
115 Lazy_Sum_Segment_Tree<int> payroll = {50, 45, 60, 55, 70, 48, 52, 65};
116
117 std::cout << "Initial payroll per department (in $K):\n";
118 for (size_t i = 0; i < payroll.size(); ++i)
119 std::cout << " Dept " << i << ": $" << payroll.get(i) << "K\n";
120
121 std::cout << "\nTotal payroll (all depts): $"
122 << payroll.query(0, 7) << "K\n";
123
124 // Range raise: departments 2-5 get +$10K
125 std::cout << "\nCorporate raises: departments 2-5 get +$10K\n";
126 payroll.update(2, 5, 10);
127
128 std::cout << "Total payroll (all depts): $"
129 << payroll.query(0, 7) << "K\n";
130 std::cout << "Payroll for depts 2-5: $"
131 << payroll.query(2, 5) << "K\n";
132
133 // Another raise: departments 0-3 get +$5K
134 std::cout << "\nAnother raise: departments 0-3 get +$5K\n";
135 payroll.update(0, 3, 5);
136
137 std::cout << "Updated payroll per department:\n";
138 for (size_t i = 0; i < payroll.size(); ++i)
139 std::cout << " Dept " << i << ": $" << payroll.get(i) << "K\n";
140
141 std::cout << "Total payroll: $" << payroll.query(0, 7) << "K\n";
142
143 std::cout << "\n";
144}
145
147{
148 std::cout << "=== SCENARIO 3: Balanceo de Servidores (Beats) ===\n\n";
149 std::cout << "Data center: 8 racks with varying CPU load (%).\n\n";
150
151 Segment_Tree_Beats<int> loads = {75, 90, 45, 60, 85, 30, 95, 50};
152
153 std::cout << "Initial loads per rack:\n";
154 for (size_t i = 0; i < loads.size(); ++i)
155 std::cout << " Rack " << i << ": " << loads.get(i) << "%\n";
156
157 std::cout << "\nTotal load: " << loads.query_sum(0, 7) << "%\n";
158 std::cout << "Max load: " << loads.query_max(0, 7) << "%\n";
159 std::cout << "Min load: " << loads.query_min(0, 7) << "%\n";
160
161 // Cap all loads at 80% (throttle overloaded servers)
162 std::cout << "\nOperations: cap all loads at 80% (chmin)\n";
163 loads.chmin(0, 7, 80);
164
165 std::cout << "After capping:\n";
166 for (size_t i = 0; i < loads.size(); ++i)
167 std::cout << " Rack " << i << ": " << loads.get(i) << "%\n";
168 std::cout << "Total load: " << loads.query_sum(0, 7) << "%\n";
169 std::cout << "Max load: " << loads.query_max(0, 7) << "%\n";
170
171 // Set minimum floor at 50% (ensure baseline utilisation)
172 std::cout << "\nOperations: set minimum floor at 50% for racks 0-3 (chmax)\n";
173 loads.chmax(0, 3, 50);
174
175 std::cout << "After floor:\n";
176 for (size_t i = 0; i < loads.size(); ++i)
177 std::cout << " Rack " << i << ": " << loads.get(i) << "%\n";
178 std::cout << "Total load: " << loads.query_sum(0, 7) << "%\n";
179
180 std::cout << "\n";
181}
182
184{
185 std::cout << "=== SCENARIO 4: RMQ dinamico vs estatico ===\n\n";
186
187 const std::vector<int> data = {9, 4, 7, 1, 8, 2, 6, 3, 5, 0};
188
189 // Static: Sparse Table — O(1) query, no updates
191
192 // Dynamic: Segment Tree — O(log n) query, O(log n) updates
194
195 std::cout << "Data: {9, 4, 7, 1, 8, 2, 6, 3, 5, 0}\n\n";
196
197 std::cout << "Query | Sparse Table (O(1)) | Segment Tree (O(lg n))\n";
198 std::cout << "----------|--------------------|-----------------------\n";
199
200 auto show_query = [&](size_t l, size_t r) {
201 std::cout << "[" << l << ", " << r << "] | "
202 << std::setw(19) << sparse.query(l, r) << " | "
203 << std::setw(21) << segtree.query(l, r) << "\n";
204 };
205
206 show_query(0, 9);
207 show_query(2, 6);
208 show_query(5, 8);
209
210 std::cout << "\nNow update a[3] = 100 (only Segment Tree supports this):\n";
211 segtree.set(3, 100);
212
213 std::cout << "Segment Tree min[0, 9] after update: "
214 << segtree.query(0, 9) << "\n";
215 std::cout << "Sparse Table min[0, 9] (unchanged): "
216 << sparse.query(0, 9) << "\n";
217
218 std::cout << "\nWhen to use each:\n";
219 std::cout << " Sparse Table: static data, many queries, O(1) per query\n";
220 std::cout << " Segment Tree: dynamic data with updates, O(lg n) per query\n";
221 std::cout << " Fenwick Tree: dynamic data, invertible operation (e.g. sum)\n";
222}
223
value_type get(const size_t i) const
Retrieve the value a[i].
T get(const size_t i) const
Retrieve the value a[i].
Ji Driver's Segment Tree (Segment Tree Beats).
T get(const size_t i) const
Retrieve the value at position i.
Main namespace for Aleph-w library functions.
Definition ah-arena.H:89
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.
static void scenario_2_ajustes_salariales()
static void scenario_1_el_arbol_del_tiempo()
static void scenario_3_balanceo_servidores()
static void scenario_4_rmq_comparison()
int main()
Lazy segment tree for range add + range sum.
Min Segment Tree for range minimum queries with point updates.
Sparse Table for range minimum queries.
gsl_rng * r
Segment trees for dynamic range queries with lazy propagation.
Sparse Table for static range queries in O(1).
DynList< int > l