1#[macro_export]
2macro_rules! count {
3 () => (0usize);
4 ( $x:tt $($xs:tt)* ) => (1usize + count!($($xs)*));
5}
6
7#[macro_export]
8macro_rules! graph {
9 (
10 with_node: $node:expr,
11 with_edges: $type:tt,
12 nodes: [$($ident:expr),*],
13 connections: [ $($from:expr => {$(($cost:expr) $to:expr),+}),* ]
14 ) => {
15 graph!{
16 nodes: [$($ident => $node),*],
17 connections: [ $($from => {$(($type, $cost) {$to}),+}),* ]
18 }
19 };
20
21 (
22 nodes: [$($ident:expr => $node:expr),*],
23 connections: [ $($from:expr => {$(($type:tt, $cost:expr) {$($to:expr),+}),+}),* ]
24 ) => {{
25
26 let mut g = Graph::with_capacity(count!($($node)*), count!($($({$from;$($to)+})+)*) );
27 $(g.register($ident, $node).unwrap());*;
28 $(
29 $($(g.$type($from, $to,$cost).unwrap());+);+
30 );*;
31 g
32 }};
33}
34
35use fixedbitset::FixedBitSet;
36use num::{One, Zero};
37pub use petgraph;
38pub use petgraph::Direction;
39use petgraph::{
40 algo::Measure,
41 graph::{EdgeIndex, NodeIndex},
42 stable_graph::{DefaultIx, IndexType},
43 visit::{VisitMap, Visitable},
44 Directed, EdgeType, Graph as PGraph,
45};
46use unicase::Ascii;
47
48use std::{
49 collections::{HashMap, VecDeque},
50 fmt::Debug,
51 hash::Hash,
52 rc::Rc,
53};
54
55#[derive(Clone, Debug)]
56pub struct Step<S, Ix> {
57 pub caller: Option<Rc<Step<S, Ix>>>,
58 pub idx: NodeIndex<Ix>,
59 pub rel: Option<EdgeIndex>,
60 pub state: S,
61}
62
63#[derive(Debug)]
64pub struct StepUnit<Ix> {
65 pub caller: Option<Rc<StepUnit<Ix>>>,
66 pub idx: NodeIndex<Ix>,
67 pub rel: Option<EdgeIndex>,
68}
69
70impl<Ix: IndexType> StepUnit<Ix> {
71 pub fn from_step<S>(step: Rc<Step<S, Ix>>) -> Rc<Self> {
72 Rc::new(Self {
73 caller: step
74 .caller
75 .as_ref()
76 .and_then(|step| Some(Self::from_step(step.clone()))),
77 idx: step.idx,
78 rel: step.rel,
79 })
80 }
81 pub fn make_void<S>(step: Rc<Step<S, Ix>>) -> Step<(), Ix> {
82 Step {
83 caller: step
84 .caller
85 .as_ref()
86 .and_then(|step| Some(Rc::new(Self::make_void(step.clone())))),
87 idx: step.idx,
88 rel: step.rel,
89 state: (),
90 }
91 }
92 pub fn into_step(step: Rc<StepUnit<Ix>>) -> Step<(), Ix> {
93 Step {
94 caller: step
95 .caller
96 .as_ref()
97 .and_then(|step| Some(Rc::new(Self::into_step(step.clone())))),
98 idx: step.idx,
99 rel: step.rel,
100 state: (),
101 }
102 }
103}
104
105#[derive(Debug)]
106pub struct Steps<S, Ix = DefaultIx> {
107 start: Option<Rc<Step<S, Ix>>>,
108}
109
110impl<S: Debug, Ix: Debug> IntoIterator for Step<S, Ix> {
111 type IntoIter = Steps<S, Ix>;
112 type Item = Rc<Step<S, Ix>>;
113 fn into_iter(self) -> Self::IntoIter {
114 Steps {
115 start: Some(Rc::new(self)),
116 }
117 }
118}
119
120impl<S: Debug, Ix: Debug> Iterator for Steps<S, Ix> {
121 type Item = Rc<Step<S, Ix>>;
122 fn next(&mut self) -> Option<Self::Item> {
123 let head = self.start.clone();
124 self.start = head.as_ref().and_then(|head| head.caller.clone());
125 head.and_then(|head| Some(head))
126 }
127}
128
129impl<S, Ix> Steps<S, Ix> {
130 pub fn from_step(step: Rc<Step<S, Ix>>) -> Self {
131 Self { start: Some(step) }
132 }
133}
134
135#[derive(Debug)]
136pub enum WalkerState<S, Ix = DefaultIx> {
137 Done,
138 Found(Step<S, Ix>),
139 NotFound(Rc<Step<S, Ix>>),
140 Cutoff,
141}
142
143pub trait Walker<S, Ix = DefaultIx> {
144 fn step(&mut self) -> WalkerState<S, Ix>;
145}
146
147#[derive(Clone)]
148pub struct BreadthFirst<'a, I, N, E, Ty, Ix> {
149 goal: Option<NodeIndex<Ix>>,
150 graph: &'a Graph<I, N, E, Ty, Ix>,
151 border: VecDeque<Step<(), Ix>>,
152 visited: FixedBitSet,
153 pub direction: Direction,
154}
155
156#[derive(Clone)]
157pub struct Dijkstra<'a, F, K, I, N, E, Ty, Ix> {
158 goal: Option<NodeIndex<Ix>>,
159 graph: &'a Graph<I, N, E, Ty, Ix>,
160 border: VecDeque<Step<K, Ix>>,
161 pub direction: Direction,
162 edge_cost: F,
163}
164
165#[derive(Clone)]
166pub struct DepthFirst<'a, D, I, N, E, Ty, Ix> {
167 goal: Option<NodeIndex<Ix>>,
168 graph: &'a Graph<I, N, E, Ty, Ix>,
169 border: VecDeque<Step<D, Ix>>,
170 limit: Option<D>,
171 cutoff: bool,
172 level: D,
173 pub direction: Direction,
174}
175
176impl<'a, D: Zero, I, N, E, Ty: EdgeType, Ix: IndexType> DepthFirst<'a, D, I, N, E, Ty, Ix> {
177 #[allow(dead_code)]
178 pub fn new(
179 graph: &'a Graph<I, N, E, Ty, Ix>,
180 start: NodeIndex<Ix>,
181 goal: Option<NodeIndex<Ix>>,
182 limit: Option<D>,
183 direction: Direction,
184 ) -> Self {
185 Self {
186 graph,
187 goal,
188 limit,
189 border: {
190 let mut border = VecDeque::with_capacity(graph.node_count());
191 border.push_front(Step {
192 caller: None,
193 idx: start,
194 rel: None,
195 state: Zero::zero(),
196 });
197 border
198 },
199 cutoff: false,
200 level: Zero::zero(),
201 direction,
202 }
203 }
204}
205
206impl<'a, D, I, N, E, Ty: EdgeType, Ix: IndexType> Walker<D, Ix>
207 for DepthFirst<'a, D, I, N, E, Ty, Ix>
208where
209 D: Measure + Copy + One + Zero,
210{
211 fn step(&mut self) -> WalkerState<D, Ix> {
212 if let Some(parent) = self.border.pop_front() {
213 if self
214 .limit
215 .and_then(|limit| Some(parent.state == limit))
216 .unwrap_or(false)
217 {
218 if self
219 .graph
220 .inner
221 .neighbors_directed(parent.idx.into(), self.direction)
222 .count()
223 != 0
224 {
225 self.cutoff = true;
226 }
227 return WalkerState::NotFound(Rc::new(parent));
228 }
229 if self
230 .goal
231 .and_then(|goal| Some(goal == parent.idx))
232 .unwrap_or(false)
233 {
234 return WalkerState::Found(parent.clone());
235 }
236
237 let parent = Rc::new(parent);
238 self.level = parent.state + One::one();
239 for child in self
240 .graph
241 .inner
242 .neighbors_directed(parent.idx.into(), self.direction)
243 {
244 self.border.push_front(Step {
245 caller: Some(parent.clone()),
246 idx: child,
247 rel: None,
248 state: self.level,
249 })
250 }
251 WalkerState::NotFound(parent)
252 } else {
253 WalkerState::Done
254 }
255 }
256}
257
258impl<'a, F: FnMut(&E) -> K, K: Zero, I, N, E, Ty: EdgeType, Ix: IndexType>
259 Dijkstra<'a, F, K, I, N, E, Ty, Ix>
260{
261 #[allow(dead_code)]
262 pub fn new(
263 graph: &'a Graph<I, N, E, Ty, Ix>,
264 start: NodeIndex<Ix>,
265 goal: Option<NodeIndex<Ix>>,
266 direction: Direction,
267 edge_cost: F,
268 ) -> Self {
269 Self {
270 goal,
271 graph,
272 border: {
273 let mut border = VecDeque::with_capacity(graph.node_count());
274 border.push_front(Step {
275 caller: None,
276 idx: start,
277 rel: None,
278 state: Zero::zero(),
279 });
280 border
281 },
282 direction,
283 edge_cost,
284 }
285 }
286}
287
288impl<'a, F, K, I, N, E, Ty: EdgeType, Ix: IndexType> Walker<K, Ix>
289 for Dijkstra<'a, F, K, I, N, E, Ty, Ix>
290where
291 K: Measure + Copy + Ord,
292 F: FnMut(&E) -> K,
293 EdgeIndex: From<EdgeIndex<Ix>>,
294{
295 fn step(&mut self) -> WalkerState<K, Ix> {
296 if let Some(parent) = {
297 let i = self
298 .border
299 .iter()
300 .enumerate()
301 .min_by(|(_, s1), (_, s2)| s1.state.cmp(&s2.state))
302 .map(|(x, _)| x);
303 i.map(|i| self.border.remove(i).unwrap())
304 } {
305 let parent = Rc::new(parent);
306 for child_idx in self
307 .graph
308 .inner
309 .neighbors_directed(parent.idx.into(), self.direction)
310 {
311 let es_goal = self
312 .goal
313 .and_then(|goal| Some(goal == child_idx))
314 .unwrap_or(false);
315 let tiene_hijos = self
316 .graph
317 .inner
318 .neighbors_directed(child_idx, self.direction)
319 .count()
320 != 0;
321 if es_goal || tiene_hijos {
322 let edge = self
323 .graph
324 .inner
325 .find_edge_undirected(parent.idx, child_idx)
326 .unwrap();
327 let step = Step {
328 caller: Some(parent.clone()),
329 idx: child_idx.into(),
330 rel: Some(edge.0.into()),
331 state: parent.state + (self.edge_cost)(&self.graph.inner[edge.0]),
332 };
333
334 if es_goal {
335 return WalkerState::Found(step);
336 }
337 self.border.push_front(step)
338 }
339 }
340 WalkerState::NotFound(parent)
341 } else {
342 WalkerState::Done
343 }
344 }
345}
346
347impl<'a, I, N, E, Ty: EdgeType, Ix: IndexType> BreadthFirst<'a, I, N, E, Ty, Ix> {
348 #[allow(dead_code)]
349 pub fn new(
350 graph: &'a Graph<I, N, E, Ty, Ix>,
351 start: NodeIndex<Ix>,
352 goal: Option<NodeIndex<Ix>>,
353 direction: Direction,
354 ) -> Self {
355 Self {
356 goal,
357 graph,
358 border: {
359 let mut border = VecDeque::with_capacity(graph.node_count());
360 border.push_front(Step {
361 caller: None,
362 idx: start,
363 rel: None,
364 state: (),
365 });
366 border
367 },
368 visited: graph.visit_map(),
369 direction,
370 }
371 }
372}
373
374impl<'a, I, N, E, Ty: EdgeType, Ix: IndexType> Walker<(), Ix>
375 for BreadthFirst<'a, I, N, E, Ty, Ix>
376{
377 fn step(&mut self) -> WalkerState<(), Ix> {
378 if let Some(parent) = self.border.pop_front() {
379 if self
380 .goal
381 .and_then(|goal| Some(goal == parent.idx))
382 .unwrap_or(false)
383 {
384 return WalkerState::Found(parent);
385 }
386
387 let parent = Rc::new(parent);
388 self.graph
389 .inner
390 .neighbors_directed(parent.idx.into(), self.direction)
391 .for_each(|child_idx| {
392 (!self.visited.is_visited(&child_idx)).then(|| {
393 self.visited.visit(child_idx);
394 self.border.push_back(Step {
395 caller: Some(parent.clone()),
396 idx: child_idx.into(),
397 rel: None,
398 state: (),
399 });
400 });
401 });
402 WalkerState::NotFound(parent)
403 } else {
404 WalkerState::Done
405 }
406 }
407}
408
409pub struct Graph<I, N, E, Ty = Directed, Ix = DefaultIx> {
426 inner: PGraph<N, E, Ty, Ix>,
428 pub nodes: HashMap<Ascii<I>, NodeIndex<Ix>>,
430}
431
432impl<I, N, E, Ty, Ix> Graph<I, N, E, Ty, Ix>
433where
434 Ty: EdgeType,
435 Ix: IndexType,
436{
437 pub fn new() -> Self {
439 Self {
440 inner: PGraph::<N, E, Ty, Ix>::default(),
441 nodes: HashMap::new(),
442 }
443 }
444
445 pub fn with_capacity(nodes: usize, edges: usize) -> Self {
449 Self {
450 inner: PGraph::with_capacity(nodes, edges),
451 nodes: HashMap::with_capacity(nodes),
452 }
453 }
454
455 pub fn node_count(&self) -> usize {
456 self.inner.node_count()
457 }
458
459 pub fn edge_count(&self) -> usize {
460 self.inner.edge_count()
461 }
462
463 pub fn visit_map(&self) -> FixedBitSet {
464 self.inner.visit_map()
465 }
466}
467
468impl<I, N, E, Ty: EdgeType, Ix: IndexType> Graph<I, N, E, Ty, Ix>
469where
470 I: Copy + Hash + Eq,
471 Ascii<I>: Copy + Hash + Eq,
472 NodeIndex: From<NodeIndex<Ix>>,
473 EdgeIndex: From<EdgeIndex<Ix>>,
474{
475 pub fn index_name<'a>(&'a self, value: NodeIndex<Ix>) -> Option<I> {
477 self.nodes.iter().find_map(|(key, val)| {
478 if val == &value {
479 Some(key.into_inner())
480 } else {
481 None
482 }
483 })
484 }
485
486 pub fn name_index(&self, ident: I) -> Option<NodeIndex<Ix>> {
488 self.nodes.get(&Ascii::new(ident)).copied()
489 }
490
491 pub fn next(&mut self, from: I, to: I, edge: E) -> Result<(), ()>
499 where
500 I: Debug,
501 {
502 match (self.name_index(from), self.name_index(to)) {
503 (Some(fidx), Some(tidx)) => {
504 self.inner.add_edge(fidx.into(), tidx.into(), edge);
505 Ok(())
506 }
507 (None, None) => panic!("Los nodos {:?} y {:?} no existen", from, to),
508 (None, Some(_)) => panic!("El nodo {:?} no existe", from),
509 (Some(_), None) => panic!("El nodo {:?} no existe", to),
510 }
511 }
512
513 pub fn register(&mut self, ident: I, node: N) -> Result<(), ()>
521 where
522 I: Debug,
523 {
524 let ascii = Ascii::new(ident);
525 if self.nodes.contains_key(&ascii) {
526 panic!("El nodo {:?} ya existe", ident);
527 } else {
528 let ix = self.inner.add_node(node);
529 self.nodes.insert(ascii, ix);
530 Ok(())
531 }
532 }
533
534 pub fn iterative_depth_first<D>(
535 &self,
536 start: I,
537 goal: Option<I>,
538 limit: Option<D>,
539 ) -> Result<Step<D, Ix>, ()>
540 where
541 D: Measure + Copy + One + Zero,
542 {
543 match goal {
544 Some(goal) => {
545 match (self.name_index(start), self.name_index(goal)) {
546 (Some(fidx), Some(tidx)) => {
547 let mut cur_limit: D = One::one();
548 loop {
549 if limit
550 .and_then(|limit| Some(limit == cur_limit))
551 .unwrap_or(false)
552 {
553 return Err(());
554 }
555 match self.depth_first_impl::<D>(fidx, Some(tidx), Some(cur_limit)) {
556 Ok(res) => {
557 return Ok(res);
558 }
559 Err(err) => match err {
560 WalkerState::Done => {
561 return Err(());
562 }
563 WalkerState::Cutoff => {
564 cur_limit = cur_limit + One::one();
565 continue;
566 },
567 _ => unreachable!("Only WalkerState::Done and WalkerState::Cutoff are returned")
568 },
569 }
570 }
571 }
572 (None, None) => Err(()),
573 (None, Some(_)) => Err(()),
574 (Some(_), None) => Err(()),
575 }
576 }
577 _ => match self.name_index(start) {
578 Some(fidx) => self.depth_first_impl(fidx, None, limit).map_err(|_| ()),
579 _ => Err(()),
580 },
581 }
582 }
583
584 pub fn depth_first<D>(
585 &self,
586 start: I,
587 goal: Option<I>,
588 limit: Option<D>,
589 ) -> Result<Step<D, Ix>, ()>
590 where
591 D: Measure + Copy + One + Zero,
592 {
593 match goal {
594 Some(goal) => match (self.name_index(start), self.name_index(goal)) {
595 (Some(fidx), Some(tidx)) => self
596 .depth_first_impl::<D>(fidx, Some(tidx), limit)
597 .map_err(|_| ()),
598 (None, None) => Err(()),
599 (None, Some(_)) => Err(()),
600 (Some(_), None) => Err(()),
601 },
602 _ => match self.name_index(start) {
603 Some(fidx) => self.depth_first_impl(fidx, None, limit).map_err(|_| ()),
604 _ => Err(()),
605 },
606 }
607 }
608
609 pub fn depth_first_impl<D>(
610 &self,
611 start: NodeIndex<Ix>,
612 goal: Option<NodeIndex<Ix>>,
613 limit: Option<D>,
614 ) -> Result<Step<D, Ix>, WalkerState<D, Ix>>
615 where
616 D: Measure + Copy + One + Zero + Debug,
617 {
618 let mut border = VecDeque::with_capacity(self.node_count());
619 border.push_front(Step {
620 caller: None,
621 idx: start,
622 rel: None,
623 state: Zero::zero(),
624 });
625 let mut cutoff = false;
626 let mut nivel;
627
628 while let Some(parent) = border.pop_front() {
629 if limit
630 .and_then(|limit| Some(parent.state == limit))
631 .unwrap_or(false)
632 {
633 if self
634 .inner
635 .neighbors_directed(parent.idx.into(), Direction::Outgoing)
636 .count()
637 != 0
638 {
639 cutoff = true;
640 }
641 continue;
642 }
643 if goal
644 .and_then(|goal| Some(goal == parent.idx))
645 .unwrap_or(false)
646 {
647 return Ok(parent.clone());
648 }
649
650 nivel = parent.state + One::one();
651 for child in self
652 .inner
653 .neighbors_directed(parent.idx.into(), petgraph::Direction::Outgoing)
654 {
655 border.push_front(Step {
656 caller: Some(Rc::new(parent.clone())),
657 idx: child,
658 rel: None,
659 state: nivel,
660 })
661 }
662 }
663
664 if cutoff {
665 Err(WalkerState::Cutoff)
666 } else {
667 Err(WalkerState::Done)
668 }
669 }
670
671 pub fn breadth_first(&self, start: I, goal: Option<I>) -> Result<Steps<(), Ix>, ()> {
672 match goal {
673 Some(goal) => match (self.name_index(start), self.name_index(goal)) {
674 (Some(fidx), Some(tidx)) => self.breadth_first_impl(fidx, Some(tidx)),
675 (None, None) => Err(()),
676 (None, Some(_)) => Err(()),
677 (Some(_), None) => Err(()),
678 },
679 _ => match self.name_index(start) {
680 Some(fidx) => self.breadth_first_impl(fidx, None),
681 _ => Err(()),
682 },
683 }
684 }
685
686 pub fn dijkstra<K, F>(
687 &self,
688 start: I,
689 goal: Option<I>,
690 edge_cost: F,
691 ) -> Result<Steps<K, Ix>, ()>
692 where
693 K: Measure + Copy + Eq + Default + Ord + PartialOrd,
694 F: FnMut(&E) -> K,
695 {
696 match goal {
697 Some(goal) => match (self.name_index(start), self.name_index(goal)) {
698 (Some(fidx), Some(tidx)) => self.dijkstra_impl(fidx, Some(tidx), edge_cost),
699 (None, None) => Err(()),
700 (None, Some(_)) => Err(()),
701 (Some(_), None) => Err(()),
702 },
703 _ => match self.name_index(start) {
704 Some(fidx) => self.dijkstra_impl(fidx, None, edge_cost),
705 _ => Err(()),
706 },
707 }
708 }
709
710 pub fn dijkstra_impl<'a, K, F>(
711 &self,
712 start: NodeIndex<Ix>,
713 goal: Option<NodeIndex<Ix>>,
714 mut edge_cost: F,
715 ) -> Result<Steps<K, Ix>, ()>
716 where
717 K: Measure + Copy + Eq + Default + Ord + PartialOrd,
718 F: FnMut(&E) -> K,
719 {
720 let mut border = VecDeque::with_capacity(self.inner.node_count());
721 border.push_front(Step {
722 caller: None,
723 idx: start,
724 rel: None,
725 state: K::default(),
726 });
727
728 while let Some(parent) = {
729 let i = border
730 .iter()
731 .enumerate()
732 .min_by(|(_, s1), (_, s2)| s1.state.cmp(&s2.state))
733 .map(|(x, _)| x);
734 i.map(|i| border.remove(i).unwrap())
735 } {
736 if goal
737 .and_then(|goal| Some(goal == parent.idx))
738 .unwrap_or(false)
739 {
740 return Ok(parent.into_iter());
741 }
742
743 let parent = Rc::new(parent);
744 for child_idx in self
745 .inner
746 .neighbors_directed(parent.idx.into(), petgraph::Direction::Outgoing)
747 {
748 let es_goal = goal
749 .and_then(|goal| Some(goal == child_idx))
750 .unwrap_or(false);
751 let tiene_hijos = self
752 .inner
753 .neighbors_directed(child_idx, petgraph::Direction::Outgoing)
754 .count()
755 != 0;
756 if es_goal || tiene_hijos {
757 let edge = self.inner.find_edge(parent.idx, child_idx).unwrap();
758 let step = Step {
759 caller: Some(parent.clone()),
760 idx: child_idx.into(),
761 rel: Some(edge.into()),
762 state: parent.state + edge_cost(&self.inner[edge]),
763 };
764
765 if es_goal {
766 return Ok(step.into_iter());
767 }
768 border.push_front(step)
769 }
770 }
771 }
772 Err(())
773 }
774
775 pub fn breadth_first_impl(
776 &self,
777 start: NodeIndex<Ix>,
778 goal: Option<NodeIndex<Ix>>,
779 ) -> Result<Steps<(), Ix>, ()> {
780 let mut border = VecDeque::with_capacity(self.inner.node_count());
781 let mut visited = self.inner.visit_map();
782 border.push_front(Step {
783 caller: None,
784 idx: start,
785 rel: None,
786 state: (),
787 });
788
789 while let Some(parent) = border.pop_front() {
790 if goal
791 .and_then(|goal| Some(goal == parent.idx))
792 .unwrap_or(false)
793 {
794 return Ok(parent.into_iter());
795 }
796
797 if self
798 .inner
799 .neighbors_directed(parent.idx.into(), petgraph::Direction::Outgoing)
800 .count()
801 != 0
802 {
803 let parent = Rc::new(parent);
804 self.inner
805 .neighbors_directed(parent.idx.into(), petgraph::Direction::Outgoing)
806 .for_each(|child_idx| {
807 (!visited.is_visited(&child_idx)).then(|| {
808 visited.visit(child_idx);
809 border.push_back(Step {
810 caller: Some(parent.clone()),
811 idx: child_idx.into(),
812 rel: None,
813 state: (),
814 });
815 });
816 });
817 }
818 }
819 Err(())
820 }
821
822 pub fn bidirectional<S: Debug, D: Debug>(
823 &self,
824 mut algo1: impl Walker<S, Ix>,
825 mut algo2: impl Walker<D, Ix>,
826 ) -> Result<Step<(), Ix>, ()> {
827 let mut res1;
828 let mut res2;
829 let mut visited1 = self.visit_map();
830 let mut visited2 = self.visit_map();
831
832 let mut steps1: HashMap<_, Rc<StepUnit<_>>> = HashMap::new();
833 let mut steps2: HashMap<_, Rc<StepUnit<_>>> = HashMap::new();
834
835 let mut last_step_1 = None;
836 let mut last_step_2 = None;
837 let matching_on = loop {
839 res1 = algo1.step();
842 res2 = algo2.step();
843
844 if let WalkerState::NotFound(ref node) = res1 {
845 visited1.visit(node.idx);
846 steps1.insert(node.idx, StepUnit::from_step(node.clone()));
847 last_step_1 = Some(StepUnit::from_step(node.clone()));
848 if visited2.is_visited(&node.idx) {
849 break 1;
850 }
851 }
852
853 if let WalkerState::NotFound(ref node) = res2 {
854 visited2.visit(node.idx);
855 steps2.insert(node.idx, StepUnit::from_step(node.clone()));
856 last_step_2 = Some(StepUnit::from_step(node.clone()));
857 if visited1.is_visited(&node.idx) {
858 break 2;
859 }
860 }
861
862 if matches!(&res1, WalkerState::Done) && matches!(&res2, WalkerState::Done) {
863 return Err(());
864 }
865
866 if let WalkerState::Found(node) = res1 {
867 return Ok(StepUnit::make_void(Rc::new(node)));
868 }
869 if let WalkerState::Found(node) = res2 {
870 return Ok(StepUnit::make_void(Rc::new(node)));
871 }
872 };
873
874 if let (Some(mut last1), Some(mut last2)) = (last_step_1, last_step_2) {
876 let mut trace1 = VecDeque::new();
877 let mut trace2 = VecDeque::new();
878
879 let res1_p = (&mut last1, &mut steps1);
880 let res2_p = (&mut last2, &mut steps2);
881 if matching_on == 1 {
882 *res2_p.0 = res2_p.1.get(&res1_p.0.idx).unwrap().clone();
883 } else {
884 *res1_p.0 = res1_p.1.get(&res2_p.0.idx).unwrap().clone();
885 }
886
887 let mut last1 = Some(last1);
889 while let Some(i) = last1 {
890 trace1.push_back(i.clone());
891 last1 = i.caller.clone();
893 }
894 let mut last2 = Some(last2);
896 while let Some(i) = last2 {
897 trace2.push_back(i.clone());
898 last2 = i.caller.clone();
900 }
901
902 for i in trace1.range(1..) {
904 trace2.push_front(i.clone());
905 }
906
907 let first = trace2.pop_front().unwrap();
908 let mut result = Step {
909 caller: None,
910 idx: first.idx,
911 rel: None,
912 state: (),
913 };
914
915 while let Some(i) = trace2.pop_front() {
916 result = Step {
917 caller: Some(Rc::new(result.clone())),
918 idx: i.idx,
919 state: (),
920 rel: i.rel,
921 }
922 }
923 Ok(result)
924 } else {
925 unreachable!("This point should always have valid last steps")
926 }
927 }
928}
929
930#[cfg(test)]
931mod tests {
932 use super::*;
933
934 #[test]
935 fn test_depth() {
936 let graph = final_grap();
937 let a = graph
938 .depth_first::<u32>("Cancun", Some("Cabo San Lucas"), None)
939 .unwrap();
940
941 for node in a {
942 println!("{:#?}", graph.index_name(node.idx).unwrap());
943 }
944 }
945
946 #[test]
947 fn test_breadth() {
948 let graph = final_grap();
949 let a = graph
950 .breadth_first("Cancun", Some("Cabo San Lucas"))
951 .unwrap();
952
953 for node in a {
954 println!("{:#?}", graph.index_name(node.idx).unwrap());
955 }
956 }
957
958 #[test]
959 fn test_breadth_walker() {
960 let graph = final_grap();
961 let mut a = BreadthFirst::new(
962 &graph,
963 graph.name_index("Cabo San Lucas").unwrap(),
964 Some(graph.name_index("Cancun").unwrap()),
965 Direction::Incoming,
966 );
967
968 let a = {
969 loop {
970 match a.step() {
971 WalkerState::Found(result) => {
972 break Some(result.into_iter());
973 }
974 WalkerState::Done => {
975 break None;
976 }
977 _ => {}
978 }
979 }
980 }
981 .unwrap();
982
983 for node in a {
984 println!("{:#?}", graph.index_name(node.idx).unwrap());
985 }
986 }
987
988 #[test]
989 fn test_dijkstra() {
990 let graph = final_grap();
991 let a = graph
992 .dijkstra("Cancun", Some("Felipe Carrillo Puerto"), |state| *state)
993 .unwrap();
994
995 for node in a {
996 println!("{:#?}", graph.index_name(node.idx).unwrap());
997 }
998 }
999
1000 #[test]
1001 fn test_dijkstra_walker() {
1002 let graph = final_grap();
1003 let mut a = Dijkstra::new(
1004 &graph,
1005 graph.name_index("Felipe Carrillo Puerto").unwrap(),
1006 Some(graph.name_index("Cancun").unwrap()),
1007 Direction::Incoming,
1008 |state| *state,
1009 );
1010
1011 let a = {
1012 loop {
1014 match a.step() {
1017 WalkerState::Found(result) => {
1018 break Some(result.into_iter());
1019 }
1020 WalkerState::Done => {
1021 break None;
1022 }
1023 _ => {}
1024 }
1025 }
1026 }
1027 .unwrap();
1028
1029 for node in a {
1030 println!("{:#?}", graph.index_name(node.idx).unwrap());
1031 }
1032 }
1033
1034 #[test]
1035 fn test_bidirectional() {
1036 let graph = final_grap();
1037
1038 let a = BreadthFirst::new(
1039 &graph,
1040 graph.name_index("Cancun").unwrap(),
1041 Some(graph.name_index("Cabo San Lucas").unwrap()),
1042 Direction::Outgoing,
1043 );
1044 let b = DepthFirst::new(
1045 &graph,
1046 graph.name_index("Cancun").unwrap(),
1047 Some(graph.name_index("Cabo San Lucas").unwrap()),
1048 None::<usize>,
1049 Direction::Incoming,
1050 );
1051
1052 let res = graph.bidirectional(a, b).unwrap();
1053 for node in res {
1054 println!("{:#?}", graph.index_name(node.idx).unwrap());
1055 }
1056 }
1057
1058 fn final_grap() -> Graph<&'static str, (), u16> {
1059 let graph: Graph<&'static str, (), u16> = graph! {
1060 with_node: (),
1061 with_edges: next,
1062 nodes: [
1063 "Acapulco", "Villa Hermosa", "Guanajuato", "Cancun",
1064 "Chilpancingo", "Aguaprieta", "Alvarado", "Valladolid",
1065 "Acayucan", "Santa Ana", "Oaxaca", "Chetumal",
1066 "Tehuantepec", "Aguascalientes", "Atlacomulco", "Campeche",
1067 "Tuxtla", "Guadalajara", "Queretaro", "Felipe Carrillo Puerto",
1068 "Merida", "Chihuahua", "Janos", "Juarez", "Ojinaga", "Iguala", "Ciudad Altamirano",
1069 "Cuernavaca", "Toluca de Lerdo", "Zihuatanejo", "Ciudad del Carmen", "Ciudad Obregon",
1070 "Guaymas", "Ciudad Victoria", "Matamoros", "Soto la Marina", "Tampico", "Colima",
1071 "Morelia", "Playa Azul", "Cordoba", "Veracruz", "Culiacan", "Hidalgo del Parral",
1072 "Topolobampo", "Durango", "Mazatlan", "Torreon", "Ensenada", "San Quintin" , "Francisco Escarcega",
1073 "Manzanillo", "Salamanca", "Hermosillo", "San Luis Potosi", "Izucar de Matamoros", "La Paz",
1074 "Cabo San Lucas", "Reynosa", "Mexicalli", "San Felipe", "Tijuana", "Ciudad de Mexico", "Pachuca de Soto",
1075 "Puebla", "Tlaxcala", "Monclova", "Piedras Negras", "Monterrey", "Nuevo Laredo" , "Puerto Angel",
1076 "Tehuacan", "Tuxpan de Rodriguez Cano", "Pinotepa Nacional", "Zacatecas", "Santa Rosalia", "Santo Domingo", "Tepic", "Ciudad Juarez"
1077
1078 ],
1079 connections: [
1080 "Cancun" => {(90) "Valladolid", (100) "Felipe Carrillo Puerto"},
1081 "Valladolid" => {(90) "Felipe Carrillo Puerto"},
1082 "Felipe Carrillo Puerto" => {(60) "Campeche"},
1083 "Campeche" => {(90) "Merida", (100) "Chetumal", (90) "Ciudad del Carmen"},
1084 "Chetumal" => {(111) "Francisco Escarcega"},
1085 "Ciudad del Carmen" => {(90) "Villa Hermosa", (90) "Tuxtla"},
1086 "Villa Hermosa" => {(90) "Acayucan"},
1087 "Tuxtla" => {(90) "Acayucan"},
1088 "Acayucan" => {(80) "Tehuantepec", (110) "Alvarado"},
1089 "Alvarado" => {(100) "Oaxaca"},
1090 "Oaxaca" => {(80) "Tehuacan", (90) "Puerto Angel", (90) "Izucar de Matamoros"},
1091 "Puerto Angel" => {(100) "Pinotepa Nacional" },
1092 "Izucar de Matamoros" => {(90) "Puebla", (100) "Cuernavaca"},
1093 "Pinotepa Nacional" => {(100) "Acapulco"},
1094 "Cuernavaca" => {(100) "Ciudad de Mexico", (100) "Ciudad Altamirano"},
1095 "Puebla" => {(90) "Ciudad de Mexico", (80) "Cordoba"},
1096 "Acapulco" => {(140) "Chilpancingo"},
1097 "Ciudad de Mexico" => {(100) "Tlaxcala", (110) "Toluca de Lerdo", (90) "Queretaro", (100) "Pachuca de Soto"},
1098 "Ciudad Altamirano" => {(90) "Zihuatanejo"},
1099 "Cordoba" => {(90) "Veracruz"},
1100 "Chilpancingo" => {(90) "Iguala"},
1101 "Toluca de Lerdo" => {(100) "Ciudad Altamirano"},
1102 "Queretaro" => {(90) "Atlacomulco", (90) "Salamanca", (90) "San Luis Potosi"},
1103 "Pachuca de Soto" => {(110) "Tuxpan de Rodriguez Cano"},
1104 "Zihuatanejo" => {(90) "Playa Azul"},
1105 "Iguala" => {(100) "Cuernavaca", (110) "Ciudad Altamirano"},
1106 "Salamanca" => {(90) "Guanajuato", (90) "Guadalajara"},
1107 "San Luis Potosi" => {(90) "Zacatecas", (70) "Durango", (100) "Aguascalientes" },
1108 "Tuxpan de Rodriguez Cano" => {(100) "Tampico"},
1109 "Playa Azul" => {(100) "Morelia", (100) "Colima", (100) "Manzanillo"},
1110 "Guanajuato" => {(80) "Aguascalientes"},
1111 "Guadalajara" => {(110) "Tepic"},
1112 "Aguascalientes" =>{(70) "Guadalajara"},
1113 "Durango" => {(90) "Hidalgo del Parral", (90) "Mazatlan"},
1114 "Tampico" => {(80) "Ciudad Victoria"},
1115 "Morelia" => {(90) "Salamanca"},
1116 "Manzanillo" => {(50) "Colima", (80) "Guadalajara"},
1117 "Colima" => {(90) "Morelia", (50) "Guadalajara"},
1118 "Tepic" =>{(50) "Mazatlan"},
1119 "Hidalgo del Parral" => {(130) "Chihuahua", (110) "Topolobampo", (80) "Culiacan"},
1120 "Mazatlan" => {(90) "Culiacan"},
1121 "Ciudad Victoria" => {(80) "Soto la Marina", (80) "Matamoros", (80) "Monterrey", (80) "Durango"},
1122 "Chihuahua" => {(90) "Ciudad Juarez", (90) "Janos"},
1123 "Topolobampo" => {(90) "Ciudad Obregon"},
1124 "Culiacan" => {(110) "Topolobampo"},
1125 "Matamoros" => {(90) "Reynosa"},
1126 "Monterrey" => {(110) "Nuevo Laredo",(70) "Monclova"},
1127 "Janos" => {(110) "Aguaprieta"},
1128 "Ciudad Obregon" => {(80) "Guaymas"},
1129 "Reynosa" => {(100) "Nuevo Laredo"},
1130 "Nuevo Laredo" => {(100) "Piedras Negras"},
1131 "Monclova" => {(100) "Torreon", (90) "Ojinaga"},
1132 "Aguaprieta" => {(90) "Santa Ana"},
1133 "Guaymas" => {(90) "Hermosillo"},
1134 "Piedras Negras" => {(90) "Monclova"},
1135 "Torreon" => {(90) "Durango"},
1136 "Ojinaga" => {(90) "Chihuahua"},
1137 "Santa Ana" => {(159) "Mexicalli"},
1138 "Hermosillo" => {(100) "Santa Ana"},
1139 "Mexicalli" => {(50) "Tijuana", (70) "San Felipe"},
1140 "Tijuana" => {(30) "Ensenada"},
1141 "San Felipe" => {(50) "Ensenada"},
1142 "Ensenada" => {(90) "San Quintin"},
1143 "San Quintin" => {(140) "Santa Rosalia"},
1144 "Santa Rosalia" => {(100) "Santo Domingo"},
1145 "Santo Domingo" => {(100) "La Paz"},
1146 "La Paz" => {(40) "Cabo San Lucas"}
1147 ]
1148 };
1149 graph
1150 }
1151}