Skip to content

Commit d4fec81

Browse files
committed
wip: concepts, comments, etc...
1 parent 24dd769 commit d4fec81

4 files changed

Lines changed: 147 additions & 19 deletions

File tree

docs/cpp-gl/concepts.md

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -7,9 +7,9 @@ This page serves as the central index for all C++20 concepts used across the lib
77
88
---
99

10-
## Graph Library (GL) Concepts
10+
## Graph Library Concepts
1111

12-
The Graph Library (GL) module relies on concepts to validate identifier types and property structures at compile time.
12+
The GL module relies on concepts to validate identifier types and property structures at compile time.
1313

1414
- **[GL Traits & Concepts Documentation](gl_traits.md)**: Full API reference for the GL module.
1515
- [`gl::traits::c_id_type`](gl_traits.md#gl-traits-c-id-type): Concept defining the requirements for an identifier type.

docs/cpp-gl/gl_traits.md

Lines changed: 37 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -29,3 +29,40 @@ Ensures that any custom ID type provided to the graph library is an unsigned int
2929
template <typename T>
3030
concept c_id_type = std::unsigned_integral<T>;
3131
```
32+
33+
---
34+
35+
## **gl::traits::c_properties** {: #gl-traits-c-properties }
36+
37+
**Module:** Part of the [GL-Traits](group__GL-Traits.md) group.
38+
39+
Defines the minimal requirements for a type to be used as a property.
40+
41+
### Detailed Description
42+
43+
A valid property type must be **semiregular** (default constructible and copyable).
44+
45+
### Template Parameters
46+
47+
| Parameter | Description |
48+
| :--- | :--- |
49+
| `T` | The type to evaluate against the concept. |
50+
51+
### Definition
52+
53+
```cpp
54+
template <typename T>
55+
concept c_properties = std::semiregular<T>;
56+
```
57+
58+
---
59+
60+
## **gl::traits::c_empty_properties** {: #gl-traits-c-empty-properties }
61+
62+
**Module:** Part of the [GL-Traits](group__GL-Traits.md) group.
63+
64+
Validates if a type is specifically the `gl::empty_properties` tag.
65+
66+
### Detailed Description
67+
68+
This concept is used to specialize behavior for graph components that do not carry any user-defined data.

include/gl/types/properties.hpp

Lines changed: 106 additions & 15 deletions
Original file line numberDiff line numberDiff line change
@@ -13,16 +13,24 @@
1313

1414
namespace gl {
1515

16-
/// @brief An empty properties type.
16+
/// @ingroup GL GL-Core
17+
/// @brief A tag struct representing no user-defined properties.
1718
struct empty_properties {};
1819

20+
/// @ingroup GL GL-Core
21+
/// @brief A tag struct representing an empty property map.
1922
struct empty_properties_map {};
2023

24+
/// @ingroup GL GL-Types
25+
/// @brief A property struct providing a basic string-based naming facility.
2126
struct name_property {
27+
/// @brief The underlying string type used for the name.
2228
using value_type = std::string;
2329

30+
/// @brief The stored name string.
2431
value_type name;
2532

33+
/// @brief Assigns a new name from a string view.
2634
name_property& operator=(std::string_view name) {
2735
this->name = name;
2836
return *this;
@@ -39,17 +47,24 @@ struct name_property {
3947
return this->name <=> name;
4048
}
4149

50+
/// @brief Serializes the name property to an output stream using quoted formatting.
4251
friend std::ostream& operator<<(std::ostream& os, const name_property& property) {
4352
os << std::quoted(property.name);
4453
return os;
4554
}
4655

56+
/// @brief Deserializes the name property from an input stream using quoted formatting.
4757
friend std::istream& operator>>(std::istream& is, name_property& property) {
4858
is >> std::quoted(property.name);
4959
return is;
5060
}
5161
};
5262

63+
/// @ingroup GL GL-Types
64+
/// @brief A type-safe container for heterogeneous properties stored by string keys.
65+
///
66+
/// Uses `std::any` and `std::unordered_map` to allow runtime attachment of
67+
/// arbitrary data types to graph elements.
5368
class dynamic_properties final {
5469
public:
5570
using key_type = std::string;
@@ -66,36 +81,49 @@ class dynamic_properties final {
6681

6782
~dynamic_properties() = default;
6883

84+
/// @brief Checks if a property with the given key exists.
6985
[[nodiscard]] gl_attr_force_inline bool is_present(const key_type& key) const {
7086
return this->_property_map.contains(key);
7187
}
7288

89+
/// @brief Retrieves a reference to a property cast to the specified type.
90+
/// @tparam ValueType The expected type of the property.
91+
/// @param key The string identifier for the property.
92+
/// @throws std::bad_any_cast If the property type does not match ValueType.
7393
template <typename ValueType>
7494
[[nodiscard]] ValueType& get(const key_type& key) {
7595
return std::any_cast<ValueType&>(this->_property_map.at(key));
7696
}
7797

98+
/// @brief Sets or updates a property value.
99+
/// @tparam ValueType The type of value being stored.
78100
template <typename ValueType>
79101
requires(std::copy_constructible<ValueType>)
80102
void set(const key_type& key, const ValueType& value) {
81103
this->_property_map[key] = value;
82104
}
83105

106+
/// @brief Moves a value into the property map.
107+
/// @tparam ValueType The type of value being stored.
84108
template <typename ValueType>
85109
requires(std::move_constructible<ValueType>)
86110
void mvset(const key_type& key, ValueType&& value) {
87-
this->_property_map[key] = std::move(value);
111+
this->_property_map[key] = std::forward<ValueType>(value);
88112
}
89113

114+
/// @brief Constructs a property value in-place.
115+
/// @tparam ValueType The type of value to construct.
90116
template <typename ValueType, typename... Args>
91117
void emplace(const key_type& key, Args&&... args) {
92118
this->_property_map[key].emplace<ValueType>(std::forward<Args>(args)...);
93119
}
94120

121+
/// @brief Removes the property associated with the given key.
95122
void remove(const key_type& key) {
96123
this->_property_map.erase(key);
97124
}
98125

126+
/// @brief Returns a reference to the underlying property map.
99127
[[nodiscard]] gl_attr_force_inline property_map_type& underlying() {
100128
return this->_property_map;
101129
}
@@ -106,12 +134,15 @@ class dynamic_properties final {
106134

107135
// --- vertex properties ---
108136

137+
/// @ingroup GL GL-Types
138+
/// @brief A specialized color property for algorithms requiring binary states (e.g., bipartition).
109139
class binary_color final {
110140
public:
111-
enum class value : std::uint16_t {
112-
black = static_cast<std::uint16_t>(0),
113-
white = static_cast<std::uint16_t>(1),
114-
unset = static_cast<std::uint16_t>(2),
141+
/// @brief The discrete states available for binary coloring.
142+
enum class value : std::uint8_t {
143+
black = static_cast<std::uint8_t>(0), ///< Represents the first color state.
144+
white = static_cast<std::uint8_t>(1), ///< Represents the second color state.
145+
unset = static_cast<std::uint8_t>(2), ///< Represents an uninitialized or neutral state.
115146
};
116147

117148
binary_color() = default;
@@ -134,24 +165,26 @@ class binary_color final {
134165
[[nodiscard]] auto operator<=>(const binary_color&) const = default;
135166
[[nodiscard]] bool operator==(const binary_color&) const = default;
136167

168+
/// @brief Returns `true` if the color is either Black or White (i.e., not Unset).
137169
gl_attr_force_inline operator bool() const {
138170
return this->is_set();
139171
}
140172

173+
/// @brief Explicit check to see if the color state is not `unset`.
141174
[[nodiscard]] gl_attr_force_inline bool is_set() const {
142175
return this->_value < value::unset;
143176
}
144177

178+
/// @brief Returns the integer representation of the current color state.
145179
[[nodiscard]] gl_attr_force_inline std::underlying_type_t<value> to_underlying() const {
146180
return std::to_underlying(this->_value);
147181
}
148182

183+
/// @brief Returns a new `binary_color` representing the opposite state (Black <-> White).
149184
[[nodiscard]] gl_attr_force_inline binary_color next() const {
150185
return value{not this->to_underlying()};
151186
}
152187

153-
// TODO: iostream operators
154-
155188
private:
156189
[[nodiscard]] value _restrict(const value value) {
157190
return std::min(value, value::unset);
@@ -160,16 +193,28 @@ class binary_color final {
160193
value _value{value::unset};
161194
};
162195

196+
/// @ingroup GL GL-Types
197+
/// @brief Alias for the underlying `binary_color::value` enum.
198+
using bin_color_value = typename binary_color::value;
199+
200+
/// @ingroup GL GL-Types
201+
/// @brief A property struct wrapping a `binary_color`.
163202
struct binary_color_property {
164-
using color_type = binary_color;
165-
color_type color;
203+
binary_color color;
166204
};
167205

168-
using bin_color_value = typename binary_color::value;
169-
206+
/// @ingroup GL GL-Types
207+
/// @brief A property struct providing arithmetic weight for edges or vertices.
208+
///
209+
/// ### Template Parameters
210+
/// | Parameter | Description | Default | Constraint |
211+
/// | :--- | :--- | :--- | :--- |
212+
/// | `WeightType` | The numeric type used to store the weight value. | `double` | [c_arithmetic](gl_traits.md#gl-traits-c-arithmetic) |
170213
template <traits::c_arithmetic WeightType = double>
171214
struct weight_property {
172215
using weight_type = WeightType;
216+
217+
/// @brief The stored numeric weight.
173218
weight_type weight = static_cast<weight_type>(1ll);
174219

175220
friend std::ostream& operator<<(std::ostream& os, const weight_property& property)
@@ -189,25 +234,62 @@ struct weight_property {
189234

190235
namespace traits {
191236

237+
/// @ingroup GL GL-Traits
238+
/// @brief Defines the minimal requirements for a type to be used as a property.
239+
///
240+
/// A valid property type must be **semiregular** (default constructible and copyable).
241+
///
242+
/// @tparam T The type to evaluate against the concept.
192243
template <typename T>
193-
concept c_properties =
194-
std::semiregular<T> and std::move_constructible<T> and std::assignable_from<T&, const T&>;
195-
244+
concept c_properties = std::semiregular<T>;
245+
246+
/// @ingroup GL GL-Traits
247+
/// @brief Validates if a type is specifically the `gl::empty_properties` tag.
248+
///
249+
/// This concept is used to specialize behavior for graph components that
250+
/// do not carry any user-defined data.
251+
///
252+
/// @tparam T The type to evaluate against the concept.
196253
template <typename T>
197254
concept c_empty_properties = c_properties<T> and std::same_as<T, gl::empty_properties>;
198255

256+
/// @ingroup GL GL-Traits
257+
/// @brief Validates if a property type contains actual user-defined data.
258+
///
259+
/// Requires that the type satisfies @ref c_properties and is not the
260+
/// @ref gl::empty_properties tag.
261+
///
262+
/// @tparam T The type to evaluate against the concept.
199263
template <typename T>
200264
concept c_non_empty_properties = c_properties<T> and not c_empty_properties<T>;
201265

266+
/// @ingroup GL GL-Traits
267+
/// @brief Checks if a type/component has a nested `properties_type` that is the @ref gl::empty_properties tag.
268+
///
269+
/// @tparam T The type to evaluate against the concept.
202270
template <typename T>
203271
concept c_has_empty_properties =
204272
requires { typename T::properties_type; } and c_empty_properties<typename T::properties_type>;
205273

274+
/// @ingroup GL GL-Traits
275+
/// @brief Checks if a type/component has a nested `properties_type` that is not the @ref gl::empty_properties tag.
276+
///
277+
/// @tparam T The type to evaluate against the concept.
206278
template <typename T>
207279
concept c_has_non_empty_properties = requires {
208280
typename T::properties_type;
209281
} and not c_empty_properties<typename T::properties_type>;
210282

283+
/// @ingroup GL GL-Traits
284+
/// @brief Requirements for properties that support binary coloring algorithms.
285+
///
286+
/// Requires a property type that:
287+
/// 1. Satisfies @ref c_properties.
288+
/// 2. Has a nested `color_type`.
289+
/// 3. Has a public `color` member of the `color_type` type.
290+
/// 4. Supports construction and comparison with `gl::binary_color`.
291+
///
292+
/// @tparam T The type to evaluate against the concept.
211293
template <typename Properties>
212294
concept c_binary_color_properties_type = c_properties<Properties> and requires(Properties p) {
213295
typename Properties::color_type;
@@ -216,6 +298,15 @@ concept c_binary_color_properties_type = c_properties<Properties> and requires(P
216298
requires std::constructible_from<typename Properties::color_type, binary_color>;
217299
};
218300

301+
/// @ingroup GL GL-Traits
302+
/// @brief Requirements for properties that support arithmetic weight values.
303+
///
304+
/// Requires a property type that:
305+
/// 1. Satisfies @ref c_properties.
306+
/// 2. Has a nested `weight_type` that satisfies @ref c_arithmetic.
307+
/// 3. Has a public `weight` member of the `weight_type` type.
308+
///
309+
/// @tparam T The type to evaluate against the concept.
219310
template <typename Properties>
220311
concept c_weight_properties_type = c_properties<Properties> and requires(Properties p) {
221312
typename Properties::weight_type;

include/gl/vertex_descriptor.hpp

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -52,8 +52,8 @@ namespace gl {
5252
/// ### Template Parameters
5353
/// | Parameter | Description | Default | Constraint |
5454
/// | :--------- | :--- | :--- | :--- |
55-
/// | Properties | The type of property data attached to the vertex. | @ref gl::empty_properties "empty_properties" | @ref gl::traits::c_properties "c_properties" |
56-
/// | IdType | The underlying integer type used for the vertex ID. | @ref gl::default_id_type "default_id_type" | [c_id_type](gl_traits.md#gl-traits-c-id-type) |
55+
/// | Properties | The type of property data attached to the vertex. | @ref gl::empty_properties "empty_properties" | [**c_properties**](gl_traits.md#gl-traits-c-properties) |
56+
/// | IdType | The underlying integer type used for the vertex ID. | @ref gl::default_id_type "default_id_type" | [**c_id_type**](gl_traits.md#gl-traits-c-id-type) |
5757
template <
5858
traits::c_properties Properties = empty_properties,
5959
traits::c_id_type IdType = default_id_type>

0 commit comments

Comments
 (0)