Aleph-w 3.0
A C++ Library for Data Structures and Algorithms
Loading...
Searching...
No Matches
lazy_graph_traversal_example.cc
Go to the documentation of this file.
1
2/*
3 Aleph_w
4
5 Data structures & Algorithms
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
54#include <iostream>
55#include <string>
56
58#include <graph-traverse.H>
59#include <print_rule.H>
60#include <tpl_graph.H>
61
62using namespace Aleph;
63using namespace std;
64
65namespace
66{
68using Arc = Graph_Arc<int>;
70using Itor = Node_Arc_Iterator<Graph>;
71
72// Small social network: Alice is friends with Bob and Charlie; Bob and
73// Charlie know each other and are both friends with the Diana/Eve pair;
74// Diana is also friends with Frank, who is friends with Grace.
76{
77 Graph g;
78
79 alice = g.insert_node("Alice");
80 auto *bob = g.insert_node("Bob");
81 auto *charlie = g.insert_node("Charlie");
82 auto *diana = g.insert_node("Diana");
83 eve = g.insert_node("Eve");
84 auto *frank = g.insert_node("Frank");
85 auto *grace = g.insert_node("Grace");
86
95
96 return g;
97}
98
100{
101 cout << "[1] BFS / DFS, driven lazily from Alice\n";
102 print_rule();
103
104 cout << "BFS order: ";
106 for (Graph::Node *n : bfs.traverse(alice))
107 cout << n->get_info() << " ";
108 cout << "\n";
109
110 cout << "DFS order: ";
112 for (Graph::Node *n : dfs.traverse(alice))
113 cout << n->get_info() << " ";
114 cout << "\n\n";
115}
116
118{
119 cout << "[2] Early termination: callback-with-bool vs plain break\n";
120 print_rule();
121
122 const string target = "Eve";
123
124 // --- Eager: the visitor must remember to `return false` to stop, and
125 // the traversal machinery has to be threaded through as a callback.
126 int eager_visits = 0;
127 Graph::Node *eager_found = nullptr;
130 {
131 ++eager_visits;
132 if (n->get_info() == target)
133 {
134 eager_found = n;
135 return false; // easy to forget this line and scan the whole graph
136 }
137 return true;
138 });
139 cout << "Eager Graph_Traverse (callback) searching for \"" << target << "\":\n";
140 cout << " found=" << (eager_found != nullptr)
141 << ", nodes visited=" << eager_visits << "\n";
142
143 // --- Lazy: the search reads as an ordinary loop; `break` is all it takes.
144 int lazy_visits = 0;
145 Graph::Node *lazy_found = nullptr;
148 {
149 ++lazy_visits;
150 if (n->get_info() == target)
151 {
152 lazy_found = n;
153 break;
154 }
155 }
156 cout << "Lazy Graph_Traverse_BFS_Generator (range-for) searching for \""
157 << target << "\":\n";
158 cout << " found=" << (lazy_found != nullptr)
159 << ", nodes visited=" << lazy_visits << "\n\n";
160
161 cout << "Same node count either way — both approaches support early\n"
162 "termination. The lazy version reads as plain iteration-with-break\n"
163 "instead of a callback contract you have to get right, and it\n"
164 "composes with other range-for/`Generator` code for free.\n\n";
165}
166} // namespace
167
168int main()
169{
170 cout << boolalpha;
171 cout << "\n=== Lazy graph BFS/DFS ===\n\n";
172
173 Graph::Node *alice = nullptr;
174 Graph::Node *eve = nullptr;
176
179
180 cout << "Done.\n";
181 return 0;
182}
WeightedDigraph::Node Node
WeightedDigraph::Arc Arc
Graph build_social_network()
Build a sample social network graph.
Lazily traverse a graph depth-first or breadth-first.
virtual Node * insert_node(Node *node) noexcept
Insertion of a node already allocated.
Definition tpl_graph.H:525
Node Node
The graph type.
Definition tpl_graph.H:433
Arc * insert_arc(Node *src_node, Node *tgt_node, void *a)
Definition tpl_graph.H:605
Traverse a graph depth-first or breadth-first and execute a visit function.
Lazy (coroutine-based) graph traversal (DFS, BFS).
Graph traversal algorithms (DFS, BFS).
size_t blossom_maximum_cardinality_matching(const GT &g, DynDlist< typename GT::Arc * > &matching, SA sa=SA())
Alias of compute_maximum_cardinality_general_matching().
Definition Blossom.H:466
DFSResult< typename Domain::Distance > dfs(Domain &domain, typename Domain::State &state, SearchPath< typename Domain::Move > &path, const typename Domain::Distance g, const typename Domain::Distance threshold, const size_t depth, IDAStarResult< Solution, typename Domain::Distance > &result, OnSolution &on_solution)
Core recursive DFS used by IDA* for a single threshold pass.
Main namespace for Aleph-w library functions.
Definition ah-arena.H:89
bool traverse(Node *root, Op op)
void print_rule()
Prints a horizontal rule for example output separation.
Definition print_rule.H:39
STL namespace.
Arc of graph implemented with double-linked adjacency lists.
Definition tpl_graph.H:223
Node belonging to a graph implemented with a double linked adjacency list.
Definition tpl_graph.H:122
Filtered iterator of adjacent arcs of a node.
Definition tpl_graph.H:1120
Generic graph and digraph implementations.