use heapless_graphs::{
adjacency_list::map_adjacency_list::MapAdjacencyList,
containers::maps::{staticdict::Dictionary, MapTrait},
conversions::FromGraph,
edgelist::edge_list::EdgeList,
edges::EdgeStructOption,
graph::Graph,
};
fn main() {
println!("Graph Conversion Demo");
println!("====================");
println!("\n1. Converting Adjacency List to Edge List");
let mut dict = Dictionary::<usize, [usize; 2], 8>::new();
dict.insert(0, [1, 2]).unwrap(); dict.insert(1, [2, 3]).unwrap(); dict.insert(2, [3, 0]).unwrap(); dict.insert(3, [0, 1]).unwrap();
let adjacency_graph = MapAdjacencyList::new_unchecked(dict);
println!("Original adjacency list graph:");
print_graph_info(&adjacency_graph);
let edge_list_graph: EdgeList<8, usize, EdgeStructOption<16, usize>> =
EdgeList::from_graph(&adjacency_graph).unwrap();
println!("\nConverted to edge list:");
print_graph_info(&edge_list_graph);
println!("\n2. Working with the Converted Graph");
let mut adj_edges = [(0usize, 0usize); 16];
let mut edge_edges = [(0usize, 0usize); 16];
let adj_edge_slice = collect(adjacency_graph.iter_edges().unwrap(), &mut adj_edges);
let edge_edge_slice = collect(edge_list_graph.iter_edges().unwrap(), &mut edge_edges);
println!("Edge count comparison:");
println!(" Adjacency list: {} edges", adj_edge_slice.len());
println!(" Edge list: {} edges", edge_edge_slice.len());
assert_eq!(adj_edge_slice.len(), edge_edge_slice.len());
let mut adj_nodes = [0usize; 8];
let mut edge_nodes = [0usize; 8];
let adj_node_slice = collect(adjacency_graph.iter_nodes().unwrap(), &mut adj_nodes);
let edge_node_slice = collect(edge_list_graph.iter_nodes().unwrap(), &mut edge_nodes);
println!("Node count comparison:");
println!(" Adjacency list: {} nodes", adj_node_slice.len());
println!(" Edge list: {} nodes", edge_node_slice.len());
assert_eq!(adj_node_slice.len(), edge_node_slice.len());
println!("\n3. Converting a Chain Graph");
let mut chain_dict = Dictionary::<usize, [usize; 1], 8>::new();
chain_dict.insert(0, [1]).unwrap(); chain_dict.insert(1, [2]).unwrap(); chain_dict.insert(2, [3]).unwrap(); chain_dict.insert(3, [4]).unwrap();
let chain_adjacency = MapAdjacencyList::new_unchecked(chain_dict);
println!("Chain graph (adjacency list):");
print_graph_info(&chain_adjacency);
let chain_edge_list: EdgeList<8, usize, EdgeStructOption<8, usize>> =
EdgeList::from_graph(&chain_adjacency).unwrap();
println!("Chain graph (edge list):");
print_graph_info(&chain_edge_list);
println!("\n4. Converting an Empty Graph");
let empty_dict = Dictionary::<usize, [usize; 2], 8>::new();
let empty_adjacency = MapAdjacencyList::new_unchecked(empty_dict);
let empty_edge_list: EdgeList<8, usize, EdgeStructOption<8, usize>> =
EdgeList::from_graph(&empty_adjacency).unwrap();
println!("Empty graph conversions:");
println!(
" Adjacency list - nodes: {}, edges: {}",
empty_adjacency.iter_nodes().unwrap().count(),
empty_adjacency.iter_edges().unwrap().count()
);
let edge_list_node_count = match empty_edge_list.iter_nodes() {
Ok(iter) => iter.count(),
Err(_) => 0, };
println!(
" Edge list - nodes: {}, edges: {}",
edge_list_node_count,
empty_edge_list.iter_edges().unwrap().count()
);
println!("\nGraph conversion is useful for:");
println!("- Converting between different graph representations");
println!("- Optimizing for different use cases (space vs. query speed)");
println!("- Interfacing between different parts of an application");
println!("- Testing graph algorithms with different backing stores");
}
fn print_graph_info<G: Graph<usize>>(graph: &G)
where
G::Error: core::fmt::Debug,
{
let node_count = graph.iter_nodes().unwrap().count();
let edge_count = graph.iter_edges().unwrap().count();
println!(" Nodes: {}, Edges: {}", node_count, edge_count);
if edge_count <= 8 {
print!(" Edges: ");
for (i, (from, to)) in graph.iter_edges().unwrap().enumerate() {
if i > 0 {
print!(", ");
}
print!("{}→{}", from, to);
}
println!();
}
}
fn collect<T: Copy, I: Iterator<Item = T>>(iter: I, dest: &mut [T]) -> &mut [T] {
let slice_len = iter
.zip(dest.iter_mut())
.map(|(item, slot)| *slot = item)
.count();
&mut dest[..slice_len]
}