Sequoia
Loading...
Searching...
No Matches
GraphDetails.hpp
Go to the documentation of this file.
1
2// Copyright Oliver J. Rosten 2018. //
3// Distributed under the GNU GENERAL PUBLIC LICENSE, Version 3.0. //
4// (See accompanying file LICENSE.md or copy at //
5// https://www.gnu.org/licenses/gpl-3.0.en.html) //
7
8#pragma once
9
17
18namespace sequoia
19{
20 namespace maths
21 {
22 enum class graph_flavour { undirected, undirected_embedded, directed };
23
24 [[nodiscard]]
25 constexpr bool is_embedded(const graph_flavour gf) noexcept
26 {
27 return gf == graph_flavour::undirected_embedded;
28 }
29
30 [[nodiscard]]
31 constexpr bool is_directed(const graph_flavour gf) noexcept
32 {
33 return gf == graph_flavour::directed;
34 }
35
36 enum class edge_sharing_preference {agnostic, shared_weight, independent};
37
38 template<class T>
40
41 template<class WeightHandler, class MetaData, std::integral IndexType>
43 struct edge_init_type_generator<partial_edge<WeightHandler, MetaData, IndexType>>
44 {
46 };
47
48 template<class WeightHandler, class MetaData, std::integral IndexType>
50 struct edge_init_type_generator<embedded_partial_edge<WeightHandler, MetaData, IndexType>>
51 {
53 };
54
55 template<class T>
56 using edge_init_type_generator_t = typename edge_init_type_generator<T>::type;
57
58 namespace graph_impl
59 {
60 template<class Edge>
61 inline constexpr bool has_shared_weight_v{
62 requires{
63 typename Edge::weight_handler_type;
64 typename Edge::weight_type;
65
66 requires std::is_same_v<object::shared<typename Edge::weight_type>, typename Edge::weight_handler_type>;
67 }
68 };
69
70 [[nodiscard]]
71 constexpr std::size_t num_static_edges(const graph_flavour flavour, const std::size_t size) noexcept
72 {
73 return (flavour != graph_flavour::directed) ? 2*size : size;
74 }
75
76 template<bool Shared, class Weight>
77 using shared_to_handler_t = std::conditional_t<Shared, object::shared<Weight>, object::by_value<Weight>>;
78
79 template<class Weight>
80 [[nodiscard]]
81 constexpr bool big_weight() noexcept
82 {
83 return sizeof(Weight) > 2*sizeof(Weight*);
84 }
85
86 // Flavour to Edge
87 template<graph_flavour GraphFlavour, class Handler, class MetaData, std::integral IndexType>
88 requires object::handler<Handler>
90 {
92 };
93
94 template<class Handler, class MetaData, std::integral IndexType>
96 struct flavour_to_edge<graph_flavour::undirected_embedded, Handler, MetaData, IndexType>
97 {
99 };
100
101 template<graph_flavour GraphFlavour, class Handler, class MetaData, std::integral IndexType>
104
105 template
106 <
107 graph_flavour GraphFlavour,
108 class EdgeWeight,
109 class EdgeMetaData,
110 std::integral IndexType,
111 class EdgeStorageConfig
112 >
114 {
115 constexpr static graph_flavour flavour{GraphFlavour};
116 constexpr static edge_sharing_preference sharing_preference{EdgeStorageConfig::edge_sharing};
117
118 constexpr static bool default_weight_sharing{
119 !is_directed(GraphFlavour)
120 && (big_weight<EdgeWeight>() || !std::is_copy_constructible_v<EdgeWeight>)
121 };
122
123 constexpr static bool shared_weight_v{
124 (sharing_preference == edge_sharing_preference::shared_weight)
125 || ((sharing_preference == edge_sharing_preference::agnostic) && default_weight_sharing)
126 };
127
128 static_assert(!shared_weight_v || (GraphFlavour != graph_flavour::directed));
129 static_assert((GraphFlavour == graph_flavour::directed) || std::is_empty_v<EdgeMetaData> || std::is_empty_v<EdgeWeight> || shared_weight_v);
130
131 using handler_type = shared_to_handler_t<shared_weight_v, EdgeWeight>;
132 using edge_type = flavour_to_edge_t<GraphFlavour, handler_type, EdgeMetaData, IndexType>;
133 using storage_type = EdgeStorageConfig::template storage_type<edge_type>;
134 };
135
136 template
137 <
138 graph_flavour GraphFlavour,
139 class EdgeWeight,
140 class EdgeMetaData,
141 std::integral IndexType,
142 class EdgeStorageConfig
143 >
144 using edge_storage_generator_t = typename edge_storage_generator<GraphFlavour, EdgeWeight, EdgeMetaData, IndexType, EdgeStorageConfig>::storage_type;
145
146 template<class T>
147 inline constexpr bool has_reservable_partitions = requires(T& t) {
148 t.reserve_partition(0, 0);
149 };
150 }
151 }
152}
Various edge types for use by graphs.
Structs to enable homogenous treatment of data which is/is not handled via shared pointers.
Decoration of a partial_edge to record the location on the target node into which the edge is embedde...
Definition: Edge.hpp:328
A concrete edge containing a target index and, optionally, a weight.
Definition: Edge.hpp:303
Definition: HandlerTraits.hpp:20
Definition: GraphDetails.hpp:39
Definition: GraphDetails.hpp:90