Created
December 7, 2023 17:17
-
-
Save mboedigh/b93719b96abb3902da0e2c80f8fc750f to your computer and use it in GitHub Desktop.
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
template <typename Map> | |
concept is_associative = requires(Map& map, Map::key_type& k) { | |
typename Map::key_type; | |
typename Map::mapped_type; | |
typename Map::value_type; | |
map[k]; | |
}; | |
template <typename Graph> | |
struct NodeIndexFactory { | |
constexpr auto operator()() { | |
if constexpr (is_associative<Graph>) { | |
using adj_nodes = Graph::mapped_type; | |
return rng::range_value_t<adj_nodes>(); | |
} else { | |
using adj_nodes = rng::range_value_t<Graph>; | |
return rng::range_value_t<adj_nodes>(); | |
} | |
} | |
}; | |
template <class Graph> | |
using node_index_t = decltype(NodeIndexFactory<Graph>()()); | |
template <typename G, typename NodeId = node_index_t<G>> | |
concept Graph = requires(G& g, NodeId& n) { | |
// Note: A Graph is a structure to model pairwise relations between objects (nodes) -- wiki | |
// This Graph concept has the bare minimum functionality for an adjacency graph | |
// Specifically, graphs only store the pairwise relations for each node and don't require | |
// maintenance functions (e.g. constructing or maintaining edges) | |
// A graph is random access range (supports []) with value_type of a range with a value_type that can be | |
requires rng::range<G>; | |
requires rng::range<decltype(g[n])>; // g[i] returns a range | |
{ *g[n].begin() } -> convertible_to<NodeId>; // node_index type can be used as an index into the graph | |
}; |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment