38#include <gtest/gtest.h>
49 return g.insert_node(value);
55 return g.insert_arc(src, tgt, value);
180 for (
auto sz :
sizes)
316 for (
auto sz :
sizes)
364 for (
auto arc : arc_list)
556 for (
auto sz :
sizes)
579 const size_t N = 100;
582 for (
size_t i = 0; i <
N; ++i)
586 auto it =
nodes.get_it();
587 auto prev = it.get_curr();
589 for (it.next(); it.has_curr(); it.next())
591 auto curr = it.get_curr();
769 return a->get_info() != 0;
800 const size_t N = 1000;
803 std::vector<TestDigraph::Node*>
nodes(
N);
804 for (
size_t i = 0; i <
N; ++i)
808 for (
size_t i = 0; i <
N; ++i)
857 for (
auto sz :
sizes)
901 std::vector<TestDigraph::Node*>
nodes(
N);
902 for (
size_t i = 0; i <
N; ++i)
906 for (
size_t i = 0; i <
N; ++i)
907 for (
size_t j = 0; j <
N; ++j)
962 for (
size_t i = 1; i <=
N; ++i)
986 for (
size_t i = 1; i <=
N; ++i)
1005 const size_t N = 20;
1008 std::vector<TestDigraph::Node *>
rim(
N);
1010 for (
size_t i = 0; i <
N; ++i)
1018 for (
size_t i = 0; i <
N; ++i)
1035 const size_t DEPTH = 6;
1037 std::vector<TestDigraph::Node *>
nodes;
1040 for (
size_t level = 0; level <
DEPTH - 1; ++level)
1042 size_t start = (1 << level) - 1;
1043 size_t end = (1 << (level + 1)) - 1;
1045 for (
size_t i = start; i < end && i <
nodes.size(); ++i)
1048 nodes.push_back(left);
1052 nodes.push_back(right);
1071 const size_t N = 20;
1073 for (
size_t i = 0; i <
N; ++i)
1075 auto n =
add_node(g,
static_cast<int>(i));
1099 for (
size_t s = 0; s <
NUM_SCCS; ++s)
1102 for (
size_t i = 0; i <
SCC_SIZE; ++i)
1108 for (
size_t i = 0; i <
SCC_SIZE; ++i)
1124 for (
auto sz :
sizes)
1181 std::vector<TestDigraph::Node *> left(
LEFT_SIZE);
1182 std::vector<TestDigraph::Node *> right(
RIGHT_SIZE);
1185 left[i] =
add_node(g,
static_cast<int>(i));
1193 add_arc(g, left[i], right[j]);
1211 std::vector<TestDigraph::Node *> left(
LEFT_SIZE);
1212 std::vector<TestDigraph::Node *> right(
RIGHT_SIZE);
1215 left[i] =
add_node(g,
static_cast<int>(i));
1224 add_arc(g, left[i], right[j]);
1225 add_arc(g, right[j], left[i]);
1241 const size_t ROWS = 5;
1242 const size_t COLS = 5;
1244 std::vector<std::vector<TestDigraph::Node *>>
grid(
ROWS,
1245 std::vector<TestDigraph::Node *>(
COLS));
1247 for (
size_t r = 0; r <
ROWS; ++r)
1248 for (
size_t c = 0; c <
COLS; ++c)
1252 for (
size_t r = 0; r <
ROWS; ++r)
1253 for (
size_t c = 0; c <
COLS; ++c)
1274 const size_t ROWS = 4;
1275 const size_t COLS = 4;
1277 std::vector<std::vector<TestDigraph::Node *>>
grid(
ROWS,
1278 std::vector<TestDigraph::Node *>(
COLS));
1280 for (
size_t r = 0; r <
ROWS; ++r)
1281 for (
size_t c = 0; c <
COLS; ++c)
1285 for (
size_t r = 0; r <
ROWS; ++r)
1286 for (
size_t c = 0; c <
COLS; ++c)
1314 const size_t DEPTH = 500;
1316 std::vector<TestDigraph::Node *>
nodes(
DEPTH);
1317 for (
size_t i = 0; i <
DEPTH; ++i)
1320 for (
size_t i = 0; i + 1 <
DEPTH; ++i)
1377 for (
auto sz :
sizes)
1385 for (
auto &block : blocks)
1405 for (
int i = 0; i < 10; ++i)
1416 for (
auto sz :
sizes)
1426 const size_t N = 2000;
1428 std::vector<TestDigraph::Node *>
nodes(
N);
1429 for (
size_t i = 0; i <
N; ++i)
1433 for (
size_t i = 0; i <
N; ++i)
1437 for (
size_t i = 0; i <
N; i += 7)
1462 for (
size_t i = 0; i <
NUM_SCCS; ++i)
1464 auto a =
add_node(g,
static_cast<int>(i * 2));
1465 auto b =
add_node(g,
static_cast<int>(i * 2 + 1));
1477 for (
auto sz :
sizes)
1574 std::vector<TestDigraph::Node *>
nodes(
N);
1575 for (
size_t i = 0; i <
N; ++i)
1580 for (
size_t i = 0; i <
N; ++i)
1581 for (
size_t j = i + 1; j <
N; ++j)
1583 if ((i + j) % 2 == 0)
1604 const size_t N = 50;
1606 std::vector<TestDigraph::Node *>
nodes(
N);
1607 for (
size_t i = 0; i <
N; ++i)
1611 for (
size_t i = 0; i <
N; ++i)
1612 for (
size_t j = 0; j <
N; ++j)
1613 if (i != j && (i * 7 + j * 3) % 5 < 3)
Tarjan's algorithm for strongly connected components.
Determines if a digraph contains a cycle and constructs it.
Generic directed graph (digraph) wrapper template.
typename BaseGraph::Arc Arc
typename BaseGraph::Node Node
bool has_curr() const noexcept
Return true if the iterator has current item.
constexpr bool is_empty() const noexcept
Return true if this (as header node) is empty.
Dynamic doubly linked list with O(1) size and bidirectional access.
Dynamic singly linked list with functional programming support.
T & append(const T &item)
Append a new item by copy.
T & get_first() const
Return the first item of the list.
constexpr bool is_empty() const noexcept
Return true if list is empty.
size_t size() const noexcept
Count the number of elements of the list.
Iterator on nodes and arcs of a path.
Node * get_first_node() const
Return the first node of path; throws overflow_error if path is empty.
bool is_empty() const noexcept
Return true if the path is empty.
Node * get_last_node() const
Return the last node of path; throws overflow_error if path is empty.
Computes strongly connected components (SCCs) in a directed graph using Tarjan's algorithm.
DynArray< Graph::Node * > nodes
Main namespace for Aleph-w library functions.
Container2< typename Container1::Item_Type > filter(Container1 &container, Operation &operation)
Filter elements that satisfy operation.
DynList< T > maps(const C &c, Op op)
Classic map operation.
Arc of graph implemented with double-linked adjacency lists.
bool operator()(TestDigraph::Arc *a) const noexcept
TestDigraph::Arc * add_arc(TestDigraph &g, TestDigraph::Node *src, TestDigraph::Node *tgt, int value=0)
TestDigraph::Node * add_node(TestDigraph &g, int value)
Generic graph and digraph implementations.