Skip to content

Commit 8fe47cb

Browse files
committed
gl mst docs
1 parent bcfdb52 commit 8fe47cb

4 files changed

Lines changed: 87 additions & 4 deletions

File tree

include/gl/algorithm/pathfinding/dijkstra.hpp

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -106,7 +106,7 @@ struct dijkstra_search_node {
106106
/// > The time complexity depends on the underlying representation of `GraphType` and the priority queue overhead:
107107
/// > - **Adjacency List Representations**: \f$O((|V| + |E|) \log |V|)\f$
108108
/// > - *Includes:* @ref gl::impl::list_t "list_t" and @ref gl::impl::flat_list_t "flat_list_t".
109-
/// > - **Dense Adjacency Matrix Representations**: \f$O(|V|^2 + |E| \log |V|)\f$
109+
/// > - **Adjacency Matrix Representations**: \f$O(|V|^2 + |E| \log |V|)\f$
110110
/// > - *Includes:* @ref gl::impl::matrix_t "matrix_t" and @ref gl::impl::flat_matrix_t "flat_matrix_t".
111111
/// > - *Note:* Iterating over adjacent vertices requires scanning the entire \f$|V|\f$-length matrix row.
112112
///

include/gl/algorithm/spanning_tree/prim_mst.hpp

Lines changed: 84 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -2,6 +2,9 @@
22
// This file is part of the CPP-GL project (https://github.com/SpectraL519/cpp-gl).
33
// Licensed under the MIT License. See the LICENSE file in the project root for full license information.
44

5+
/// @file gl/algorithm/spanning_tree/prim_mst.hpp
6+
/// @brief Concrete implementations of Prim's Minimum Spanning Tree (MST) algorithm.
7+
58
#pragma once
69

710
#include "gl/algorithm/util.hpp"
@@ -12,20 +15,66 @@
1215

1316
namespace gl::algorithm {
1417

18+
/// @ingroup GL GL-Algorithm
19+
/// @brief A descriptor structure holding the results of a Minimum Spanning Tree (MST) execution.
20+
///
21+
/// @tparam G The type of the undirected graph. Must satisfy the [**c_undirected_graph**](gl_concepts.md#gl-traits-c-undirected-graph) concept.
1522
template <traits::c_undirected_graph G>
1623
struct mst_descriptor {
24+
/// @brief The type of the graph.
1725
using graph_type = G;
26+
/// @brief The type of the edges stored in the graph.
1827
using edge_type = typename graph_type::edge_type;
28+
/// @brief The numeric type used to represent accumulated tree weights.
1929
using weight_type = vertex_distance_type<graph_type>;
2030

31+
/// @brief Constructs a descriptor sized to hold the resulting tree edges.
32+
/// @param n_vertices The total number of vertices in the graph.
2133
mst_descriptor(const size_type n_vertices) {
2234
edges.reserve(n_vertices - 1uz);
2335
}
2436

37+
/// @brief The sequence of edges that form the Minimum Spanning Tree.
2538
std::vector<edge_type> edges;
39+
/// @brief The accumulated minimum weight/cost of the entire spanning tree.
2640
weight_type weight = static_cast<weight_type>(0);
2741
};
2842

43+
/// @ingroup GL GL-Algorithm
44+
/// @brief Computes the Minimum Spanning Tree (MST) of an undirected graph using Prim's algorithm with an edge-based priority queue.
45+
///
46+
/// This implementation uses a standard binary heap (`std::priority_queue`) to store and sort edges based on their weight.
47+
/// It pushes newly discovered adjacent edges into the queue and safely ignores those that lead to already-visited vertices.
48+
///
49+
/// ### Example Usage
50+
/// ```cpp
51+
/// auto mst = gl::algorithm::edge_heap_prim_mst(graph, start_id); // (1)!
52+
/// std::cout << "Total MST Weight: " << mst.weight
53+
/// << "\nMST Edges: " << gl::io::set_formatter(mst.edges) << '\n';
54+
/// ```
55+
///
56+
/// 1\. Computes the MST starting from the given `start_id`. If `invalid_id` is passed, it defaults to the graph's `initial_id`.
57+
///
58+
/// > [!INFO] Algorithmic Complexity
59+
/// >
60+
/// > The time complexity depends on the underlying representation of `GraphType` and the queue overhead:
61+
/// > - **Adjacency List Representations**: \f$O(|E| \log |E|)\f$
62+
/// > - *Includes:* @ref gl::impl::list_t "list_t" and @ref gl::impl::flat_list_t "flat_list_t".
63+
/// > - *Note:* In simple graphs, this simplifies to \f$O(|E| \log |V|)\f$. However, because list models allow multigraphs, the queue size and operations scale strictly with \f$|E|\f$.
64+
/// > - **Adjacency Matrix Representations**: \f$O(|V|^2 + |E| \log |V|)\f$
65+
/// > - *Includes:* @ref gl::impl::matrix_t "matrix_t" and @ref gl::impl::flat_matrix_t "flat_matrix_t".
66+
/// > - *Note:* Iterating over incident edges requires scanning the entire \f$|V|\f$-length matrix row. Since matrices represent simple graphs, the heap operations safely simplify to \f$O(\log |V|)\f$.
67+
///
68+
/// ### Template Parameters
69+
/// | Parameter | Description | Constraint |
70+
/// | :-------- | :--- | :--- |
71+
/// | G | The type of the undirected graph being traversed. | Must satisfy the [**c_undirected_graph**](gl_concepts.md#gl-traits-c-undirected-graph) concept. |
72+
///
73+
/// @param graph The undirected graph to evaluate.
74+
/// @param root_id The starting vertex ID for the MST calculation. Defaults to the graph's `initial_id` if `invalid_id` is passed.
75+
/// @return A @ref gl::algorithm::mst_descriptor "mst_descriptor" containing the accumulated minimum weight and the sequence of edges forming the tree.
76+
/// @see @ref gl::algorithm::vertex_heap_prim_mst "vertex_heap_prim_mst" For the vertex-heap variant of the Prim's MST finding algorithm.
77+
/// @hideparams
2978
template <traits::c_undirected_graph G>
3079
[[nodiscard]] mst_descriptor<G> edge_heap_prim_mst(const G& graph, typename G::id_type root_id) {
3180
// type definitions
@@ -83,8 +132,42 @@ template <traits::c_undirected_graph G>
83132
return mst;
84133
}
85134

135+
/// @ingroup GL GL-Algorithm
136+
/// @brief Computes the Minimum Spanning Tree (MST) of an undirected graph using Prim's algorithm with a vertex-based array heap.
137+
///
138+
/// This variation maintains a heap of vertex IDs based on their minimum known connection cost.
139+
/// Because standard C++ heaps do not support a `decrease_key` operation, this implementation
140+
/// dynamically rebuilds the heap (`std::make_heap`) at the end of each iteration to reflect updated distances.
141+
///
142+
/// ### Example Usage
143+
/// ```cpp
144+
/// auto mst = gl::algorithm::vertex_heap_prim_mst(graph, start_id); // (1)!
145+
/// std::cout << "Total MST Weight: " << mst.weight
146+
/// << "\nMST Edges: " << gl::io::set_formatter(mst.edges) << '\n';
147+
/// ```
148+
///
149+
/// 1\. Computes the MST starting from the given `start_id`. Highly optimal for dense matrix graphs.
150+
///
151+
/// > [!INFO] Algorithmic Complexity
152+
/// >
153+
/// > Due to rebuilding the heap (\f$O(|V|)\f$) up to \f$|V|\f$ times, combined with evaluating every edge, the strict time complexity is \f$O(|V|^2 + |E|)\f$:
154+
/// > - **Adjacency Matrix Representations**: \f$O(|V|^2)\f$
155+
/// > - *Note:* Since matrix models inherently represent simple graphs (where \f$|E| \le |V|^2\f$), the complexity strictly simplifies to \f$O(|V|^2)\f$. This makes the vertex heap approach highly suitable for dense graphs.
156+
/// > - **Adjacency List Representations**: \f$O(|V|^2 + |E|)\f$
157+
/// > - *Note:* For multigraphs, the edge count \f$|E|\f$ can exceed \f$|V|^2\f$, meaning the edge traversal phase will dictate the overall performance.
158+
///
159+
/// ### Template Parameters
160+
/// | Parameter | Description | Constraint |
161+
/// | :-------- | :--- | :--- |
162+
/// | G | The type of the undirected graph being traversed. | Must satisfy the [**c_undirected_graph**](gl_concepts.md#gl-traits-c-undirected-graph) concept and its @ref gl::vertex_distance_type "distance type" must satisfy [**c_has_numeric_limits_max**](gl_concepts.md#gl-traits-c-has-numeric-limits-max).
163+
///
164+
/// @param graph The undirected graph to evaluate.
165+
/// @param root_id The starting vertex ID for the MST calculation. Defaults to the graph's `initial_id` if `invalid_id` is passed.
166+
/// @return A @ref gl::algorithm::mst_descriptor "mst_descriptor" containing the accumulated minimum weight and the sequence of edges forming the tree.
167+
/// @see @ref gl::algorithm::edge_heap_prim_mst "edge_heap_prim_mst" For the vertex-heap variant of the Prim's MST finding algorithm.
168+
/// @hideparams
86169
template <traits::c_undirected_graph G>
87-
requires traits::c_has_numeric_limits_max<vertex_distance_type<G>>
170+
requires(traits::c_has_numeric_limits_max<vertex_distance_type<G>>)
88171
[[nodiscard]] mst_descriptor<G> vertex_heap_prim_mst(const G& graph, typename G::id_type root_id) {
89172
// type definitions
90173
using id_type = typename G::id_type;

include/gl/algorithm/topology/coloring.hpp

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -41,7 +41,7 @@ using bicoloring_type = std::vector<binary_color>;
4141
/// > The time complexity depends entirely on the underlying representation of `GraphType`:
4242
/// > - **Adjacency List Representations**: \f$O(|V| + |E|)\f$
4343
/// > - *Includes:* @ref gl::impl::list_t "list_t" and @ref gl::impl::flat_list_t "flat_list_t".
44-
/// > - **Dense Adjacency Matrix Representations**: \f$O(|V|^2)\f$
44+
/// > - **Adjacency Matrix Representations**: \f$O(|V|^2)\f$
4545
/// > - *Includes:* @ref gl::impl::matrix_t "matrix_t" and @ref gl::impl::flat_matrix_t "flat_matrix_t".
4646
/// > - *Note:* Iterating over adjacent vertices requires scanning the entire \f$|V|\f$-length matrix row.
4747
///

include/gl/algorithm/topology/topological_sort.hpp

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -43,7 +43,7 @@ namespace gl::algorithm {
4343
/// > The time complexity depends entirely on the underlying representation of `GraphType`:
4444
/// > - **Adjacency List Representations**: \f$O(|V| + |E|)\f$
4545
/// > - *Includes:* @ref gl::impl::list_t "list_t" and @ref gl::impl::flat_list_t "flat_list_t".
46-
/// > - **Dense Adjacency Matrix Representations**: \f$O(|V|^2)\f$
46+
/// > - **Adjacency Matrix Representations**: \f$O(|V|^2)\f$
4747
/// > - *Includes:* @ref gl::impl::matrix_t "matrix_t" and @ref gl::impl::flat_matrix_t "flat_matrix_t".
4848
/// > - *Note:* Iterating over adjacent vertices requires scanning the entire \f$|V|\f$-length matrix row.
4949
///

0 commit comments

Comments
 (0)