Advertisement
NLinker

Graph data structure in Rust

Jan 7th, 2019
419
0
Never
Not a member of Pastebin yet? Sign Up, it unlocks many cool features!
Rust 2.51 KB | None | 0 0
  1. use std::rc::{Rc, Weak};
  2. use std::cell::RefCell;
  3.  
  4. struct Vertex<V> {
  5.     value: V,
  6.     neighbours: Vec<Weak<RefCell<Vertex<V>>>>,
  7. }
  8.  
  9. type RcVertex<V> = Rc<RefCell<Vertex<V>>>;
  10.  
  11. struct Graph<V> {
  12.     vertices: Vec<RcVertex<V>>,
  13. }
  14.  
  15. impl<V> Graph<V> {
  16.     fn new() -> Self {
  17.         Graph { vertices: vec![] }
  18.     }
  19.    
  20.     fn new_vertex(&mut self, value: V) -> RcVertex<V> {
  21.         self.add_vertex(Vertex { value, neighbours: Vec::new() })
  22.     }
  23.    
  24.     fn add_vertex(&mut self, v: Vertex<V>) -> RcVertex<V> {
  25.         let v = Rc::new(RefCell::new(v));
  26.         self.vertices.push(Rc::clone(&v));
  27.         v
  28.     }
  29.    
  30.     fn add_edge(&mut self, v1: &RcVertex<V>, v2: &RcVertex<V>) {
  31.         v1.borrow_mut().neighbours.push(Rc::downgrade(&v2));
  32.         v2.borrow_mut().neighbours.push(Rc::downgrade(&v1));
  33.     }
  34.    
  35.     fn bft(start: RcVertex<V>, f: impl Fn(&V)) {
  36.         let mut q = vec![start];
  37.         let mut i = 0;
  38.         while i < q.len() {
  39.             let v = Rc::clone(&q[i]);
  40.             i += 1;
  41.             (f)(&v.borrow().value);
  42.             for n in &v.borrow().neighbours {
  43.                 let n = n.upgrade().expect("Invalid neighbour");
  44.                 if q.iter().all(|v| v.as_ptr() != n.as_ptr()) {
  45.                     q.push(n);
  46.                 }
  47.             }
  48.         }
  49.     }
  50.    
  51.     fn dft(start: RcVertex<V>, f: impl Fn(&V)) {
  52.         let mut s = vec![];
  53.         Self::dft_helper(start, &f, &mut s);
  54.     }
  55.    
  56.     fn dft_helper(start: RcVertex<V>, f: &impl Fn(&V), s: &mut Vec<*const Vertex<V>>) {
  57.         s.push(start.as_ptr());
  58.         (f)(&start.borrow().value);
  59.         for n in &start.borrow().neighbours {
  60.             let n = n.upgrade().expect("Invalid neighbor");
  61.             if s.iter().all(|&p| p != n.as_ptr()) {
  62.                 Self::dft_helper(n, f, s);
  63.             }
  64.         }
  65.     }
  66. }
  67.  
  68. fn main() {
  69.     let mut g = Graph::new();
  70.    
  71.     let v1 = g.new_vertex(1);
  72.     let v2 = g.new_vertex(2);
  73.     let v3 = g.new_vertex(3);
  74.     let v4 = g.new_vertex(4);
  75.     let v5 = g.new_vertex(5);
  76.    
  77.     g.add_edge(&v1, &v2);
  78.     g.add_edge(&v1, &v3);
  79.     g.add_edge(&v1, &v4);
  80.     g.add_edge(&v2, &v5);
  81.     g.add_edge(&v3, &v4);
  82.     g.add_edge(&v4, &v5);
  83.    
  84.     println!(r"Graph:
  85.    (1)
  86.  /  |  \
  87. (2) (3)-(4)
  88.  \     /
  89.    (5)");
  90.    
  91.     print!("Breadth-first traversing: ");
  92.     Graph::bft(v1.clone(), |v| print!("{} ", v));
  93.     println!();
  94.    
  95.     print!("Depth-first traversing: ");
  96.     Graph::dft(v1, |v| print!("{} ", v));
  97.     println!();
  98. }
Advertisement
Add Comment
Please, Sign In to add comment
Advertisement