Add GraphTopology::edges() and tests
This commit is contained in:
@@ -102,6 +102,10 @@ impl GraphTopology for AppendGraph {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
fn edges(&self) -> impl Iterator<Item = Self::Edge> {
|
||||||
|
(0..self.incidences.len()).step_by(2).map(Incidence)
|
||||||
|
}
|
||||||
|
|
||||||
fn add_vertex(&mut self) -> Self::Vertex {
|
fn add_vertex(&mut self) -> Self::Vertex {
|
||||||
self.vertices.push(VertexIncidenceHeader {
|
self.vertices.push(VertexIncidenceHeader {
|
||||||
incidence_count: 0,
|
incidence_count: 0,
|
||||||
|
|||||||
@@ -181,6 +181,13 @@ impl GraphTopology for Graph {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
fn edges(&self) -> impl Iterator<Item = Self::Edge> {
|
||||||
|
self.incidences
|
||||||
|
.iter()
|
||||||
|
.filter(|(i, _)| i.arr_idx() % 2 == 0)
|
||||||
|
.map(|(i, _)| i)
|
||||||
|
}
|
||||||
|
|
||||||
fn add_vertex(&mut self) -> Self::Vertex {
|
fn add_vertex(&mut self) -> Self::Vertex {
|
||||||
self.vertices.insert(VertexIncidenceHeader {
|
self.vertices.insert(VertexIncidenceHeader {
|
||||||
incidence_count: 0,
|
incidence_count: 0,
|
||||||
|
|||||||
@@ -2,29 +2,35 @@
|
|||||||
#[macro_export]
|
#[macro_export]
|
||||||
macro_rules! graph_topology_test_fixtures {
|
macro_rules! graph_topology_test_fixtures {
|
||||||
($T:ty) => {
|
($T:ty) => {
|
||||||
fn make_test_graph() -> ($T, [<$T as $crate::traits::GraphTopology>::Vertex; 10]) {
|
fn make_test_graph() -> (
|
||||||
|
$T,
|
||||||
|
[<$T as $crate::traits::GraphTopology>::Vertex; 10],
|
||||||
|
[<$T as $crate::traits::GraphTopology>::Edge; 18],
|
||||||
|
) {
|
||||||
let mut graph = <$T>::new();
|
let mut graph = <$T>::new();
|
||||||
let vertices: [<$T as $crate::traits::GraphTopology>::Vertex; 10] =
|
let vertices: [<$T as $crate::traits::GraphTopology>::Vertex; 10] =
|
||||||
core::array::from_fn(|_| graph.add_vertex());
|
core::array::from_fn(|_| graph.add_vertex());
|
||||||
graph.add_edge(vertices[0], vertices[1]);
|
let edges = [
|
||||||
graph.add_edge(vertices[0], vertices[1]);
|
graph.add_edge(vertices[0], vertices[1]),
|
||||||
graph.add_edge(vertices[1], vertices[2]);
|
graph.add_edge(vertices[0], vertices[1]),
|
||||||
graph.add_edge(vertices[1], vertices[3]);
|
graph.add_edge(vertices[1], vertices[2]),
|
||||||
graph.add_edge(vertices[1], vertices[4]);
|
graph.add_edge(vertices[1], vertices[3]),
|
||||||
graph.add_edge(vertices[2], vertices[2]);
|
graph.add_edge(vertices[1], vertices[4]),
|
||||||
graph.add_edge(vertices[2], vertices[4]);
|
graph.add_edge(vertices[2], vertices[2]),
|
||||||
graph.add_edge(vertices[2], vertices[4]);
|
graph.add_edge(vertices[2], vertices[4]),
|
||||||
graph.add_edge(vertices[2], vertices[5]);
|
graph.add_edge(vertices[2], vertices[4]),
|
||||||
graph.add_edge(vertices[2], vertices[6]);
|
graph.add_edge(vertices[2], vertices[5]),
|
||||||
graph.add_edge(vertices[3], vertices[6]);
|
graph.add_edge(vertices[2], vertices[6]),
|
||||||
graph.add_edge(vertices[4], vertices[4]);
|
graph.add_edge(vertices[3], vertices[6]),
|
||||||
graph.add_edge(vertices[4], vertices[7]);
|
graph.add_edge(vertices[4], vertices[4]),
|
||||||
graph.add_edge(vertices[4], vertices[8]);
|
graph.add_edge(vertices[4], vertices[7]),
|
||||||
graph.add_edge(vertices[5], vertices[9]);
|
graph.add_edge(vertices[4], vertices[8]),
|
||||||
graph.add_edge(vertices[6], vertices[9]);
|
graph.add_edge(vertices[5], vertices[9]),
|
||||||
graph.add_edge(vertices[7], vertices[8]);
|
graph.add_edge(vertices[6], vertices[9]),
|
||||||
graph.add_edge(vertices[7], vertices[9]);
|
graph.add_edge(vertices[7], vertices[8]),
|
||||||
(graph, vertices)
|
graph.add_edge(vertices[7], vertices[9]),
|
||||||
|
];
|
||||||
|
(graph, vertices, edges)
|
||||||
}
|
}
|
||||||
};
|
};
|
||||||
}
|
}
|
||||||
@@ -48,7 +54,7 @@ macro_rules! graph_topology_tests {
|
|||||||
|
|
||||||
#[test]
|
#[test]
|
||||||
fn vertex_count() {
|
fn vertex_count() {
|
||||||
let (graph, _) = make_test_graph();
|
let (graph, _, _) = make_test_graph();
|
||||||
assert_eq!(graph.vertex_count(), 10, "unexpected vertex count");
|
assert_eq!(graph.vertex_count(), 10, "unexpected vertex count");
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -69,7 +75,7 @@ macro_rules! graph_topology_tests {
|
|||||||
|
|
||||||
#[test]
|
#[test]
|
||||||
fn edge_count() {
|
fn edge_count() {
|
||||||
let (graph, _) = make_test_graph();
|
let (graph, _, _) = make_test_graph();
|
||||||
assert_eq!(graph.edge_count(), 18, "unexpected edge count");
|
assert_eq!(graph.edge_count(), 18, "unexpected edge count");
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -82,7 +88,7 @@ macro_rules! graph_topology_tests {
|
|||||||
|
|
||||||
#[test]
|
#[test]
|
||||||
fn degree() {
|
fn degree() {
|
||||||
let (graph, vertices) = make_test_graph();
|
let (graph, vertices, _) = make_test_graph();
|
||||||
let expected_degrees = [2, 5, 7, 2, 7, 2, 3, 3, 2, 3];
|
let expected_degrees = [2, 5, 7, 2, 7, 2, 3, 3, 2, 3];
|
||||||
for i in 0..graph.vertex_count() {
|
for i in 0..graph.vertex_count() {
|
||||||
assert_eq!(
|
assert_eq!(
|
||||||
@@ -118,7 +124,7 @@ macro_rules! graph_topology_tests {
|
|||||||
|
|
||||||
#[test]
|
#[test]
|
||||||
fn are_adjacent() {
|
fn are_adjacent() {
|
||||||
let (graph, vertices) = make_test_graph();
|
let (graph, vertices, _) = make_test_graph();
|
||||||
assert!(
|
assert!(
|
||||||
graph.are_adjacent(vertices[0], vertices[1]),
|
graph.are_adjacent(vertices[0], vertices[1]),
|
||||||
"expected {:?} and {:?} to be adjacent",
|
"expected {:?} and {:?} to be adjacent",
|
||||||
@@ -172,7 +178,7 @@ macro_rules! graph_topology_tests {
|
|||||||
|
|
||||||
#[test]
|
#[test]
|
||||||
fn vertices() {
|
fn vertices() {
|
||||||
let (graph, vertices) = make_test_graph();
|
let (graph, vertices, _) = make_test_graph();
|
||||||
assert_eq!(graph.vertices().count(), 10, "unexpected vertex count");
|
assert_eq!(graph.vertices().count(), 10, "unexpected vertex count");
|
||||||
|
|
||||||
// Expects each vertex to appear exactly once.
|
// Expects each vertex to appear exactly once.
|
||||||
@@ -198,7 +204,7 @@ macro_rules! graph_topology_tests {
|
|||||||
|
|
||||||
#[test]
|
#[test]
|
||||||
fn neighbors() {
|
fn neighbors() {
|
||||||
let (graph, vertices) = make_test_graph();
|
let (graph, vertices, _) = make_test_graph();
|
||||||
// Checks neighbors of vertex 4.
|
// Checks neighbors of vertex 4.
|
||||||
assert_eq!(
|
assert_eq!(
|
||||||
graph.neighbors(vertices[4]).count(),
|
graph.neighbors(vertices[4]).count(),
|
||||||
@@ -233,6 +239,31 @@ macro_rules! graph_topology_tests {
|
|||||||
);
|
);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
#[test]
|
||||||
|
fn edges_empty() {
|
||||||
|
let graph = <$T>::new();
|
||||||
|
assert_eq!(
|
||||||
|
graph.edges().count(),
|
||||||
|
0,
|
||||||
|
"edge iterator of empty graph should have no elements"
|
||||||
|
);
|
||||||
|
}
|
||||||
|
|
||||||
|
#[test]
|
||||||
|
fn edges() {
|
||||||
|
let (graph, _, edges) = make_test_graph();
|
||||||
|
assert_eq!(graph.edges().count(), 18, "unexpected edge count");
|
||||||
|
|
||||||
|
// Expects each edge to appear exactly once.
|
||||||
|
for e in graph.edges() {
|
||||||
|
assert_eq!(
|
||||||
|
edges.iter().filter(|&x| *x == e).count(),
|
||||||
|
1,
|
||||||
|
"unexpected edge {e:?} from the iterator"
|
||||||
|
);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
#[test]
|
#[test]
|
||||||
fn loop_edge() {
|
fn loop_edge() {
|
||||||
let mut graph = <$T>::new();
|
let mut graph = <$T>::new();
|
||||||
@@ -369,7 +400,7 @@ macro_rules! graph_topology_deletion_tests {
|
|||||||
|
|
||||||
#[test]
|
#[test]
|
||||||
fn delete_vertex_connected() {
|
fn delete_vertex_connected() {
|
||||||
let (mut graph, vertices) = make_test_graph();
|
let (mut graph, vertices, _) = make_test_graph();
|
||||||
assert_eq!(
|
assert_eq!(
|
||||||
graph.vertex_count(),
|
graph.vertex_count(),
|
||||||
10,
|
10,
|
||||||
@@ -556,7 +587,7 @@ macro_rules! graph_topology_deletion_tests {
|
|||||||
|
|
||||||
#[test]
|
#[test]
|
||||||
fn vertices_after_delete() {
|
fn vertices_after_delete() {
|
||||||
let (mut graph, vertices) = make_test_graph();
|
let (mut graph, vertices, _) = make_test_graph();
|
||||||
graph.delete_vertex(vertices[2]);
|
graph.delete_vertex(vertices[2]);
|
||||||
assert_eq!(
|
assert_eq!(
|
||||||
graph.vertex_count(),
|
graph.vertex_count(),
|
||||||
@@ -583,5 +614,31 @@ macro_rules! graph_topology_deletion_tests {
|
|||||||
);
|
);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
#[test]
|
||||||
|
fn edges_after_delete() {
|
||||||
|
let (mut graph, vertices, edges) = make_test_graph();
|
||||||
|
graph.delete_vertex(vertices[2]);
|
||||||
|
assert_eq!(graph.edge_count(), 12, "unexpected edge count after delete");
|
||||||
|
assert_eq!(
|
||||||
|
graph.edges().count(),
|
||||||
|
12,
|
||||||
|
"unexpected edge iterator count after delete"
|
||||||
|
);
|
||||||
|
for i in [2, 5, 6, 7, 8, 9] {
|
||||||
|
assert!(
|
||||||
|
!graph.edges().any(|e| e == edges[i]),
|
||||||
|
"deleted edge {:?} appeared in iterator",
|
||||||
|
edges[i]
|
||||||
|
);
|
||||||
|
}
|
||||||
|
for i in [0, 1, 3, 4, 10, 11, 12, 13, 14, 15, 16, 17] {
|
||||||
|
assert!(
|
||||||
|
graph.edges().any(|e| e == edges[i]),
|
||||||
|
"expected edge {:?} missing from iterator after delete",
|
||||||
|
edges[i]
|
||||||
|
);
|
||||||
|
}
|
||||||
|
}
|
||||||
};
|
};
|
||||||
}
|
}
|
||||||
|
|||||||
+1
-1
@@ -1,5 +1,4 @@
|
|||||||
// TODO: Add functions to reserve memory for vertices and edges.
|
// TODO: Add functions to reserve memory for vertices and edges.
|
||||||
// TODO: Add iterator of all edges.
|
|
||||||
// TODO: Add iterator of incident edges for a vertex.
|
// TODO: Add iterator of incident edges for a vertex.
|
||||||
// TODO: Add finding incident vertices for an edge.
|
// TODO: Add finding incident vertices for an edge.
|
||||||
// TODO: Split out GraphTopologyAddition trait.
|
// TODO: Split out GraphTopologyAddition trait.
|
||||||
@@ -13,6 +12,7 @@ pub trait GraphTopology {
|
|||||||
fn are_adjacent(&self, v1: Self::Vertex, v2: Self::Vertex) -> bool;
|
fn are_adjacent(&self, v1: Self::Vertex, v2: Self::Vertex) -> bool;
|
||||||
fn vertices(&self) -> impl Iterator<Item = Self::Vertex>;
|
fn vertices(&self) -> impl Iterator<Item = Self::Vertex>;
|
||||||
fn neighbors(&self, v: Self::Vertex) -> impl Iterator<Item = Self::Vertex>;
|
fn neighbors(&self, v: Self::Vertex) -> impl Iterator<Item = Self::Vertex>;
|
||||||
|
fn edges(&self) -> impl Iterator<Item = Self::Edge>;
|
||||||
fn add_vertex(&mut self) -> Self::Vertex;
|
fn add_vertex(&mut self) -> Self::Vertex;
|
||||||
fn add_edge(&mut self, v1: Self::Vertex, v2: Self::Vertex) -> Self::Edge;
|
fn add_edge(&mut self, v1: Self::Vertex, v2: Self::Vertex) -> Self::Edge;
|
||||||
}
|
}
|
||||||
|
|||||||
Reference in New Issue
Block a user