1pub use self::filter::*;
43pub use self::reversed::*;
44
45#[macro_use]
46mod macros;
47
48mod dfsvisit;
49mod traversal;
50pub use self::dfsvisit::*;
51pub use self::traversal::*;
52
53use fixedbitset::FixedBitSet;
54
55#[cfg(feature = "std")]
56use std::{
57 collections::HashSet,
58 hash::{BuildHasher, Hash},
59};
60
61#[cfg(not(feature = "std"))]
62use core::hash::Hash;
63
64#[cfg(not(feature = "std"))]
65use alloc::collections::BTreeSet as HashSet;
66
67use super::{graph, EdgeType};
68use crate::graph::NodeIndex;
69
70#[cfg(feature = "graphmap")]
71use crate::prelude::GraphMap;
72
73#[cfg(feature = "stable_graph")]
74use crate::prelude::StableGraph;
75use crate::prelude::{Direction, Graph};
76
77use crate::csr::Csr;
78use crate::graph::Frozen;
79use crate::graph::IndexType;
80#[cfg(feature = "stable_graph")]
81use crate::stable_graph;
82#[cfg(feature = "matrix_graph")]
83use crate::matrix_graph::MatrixGraph;
84#[cfg(feature = "graphmap")]
85use crate::graphmap::{self, NodeTrait};
86
87trait_template! {
88pub trait GraphBase {
91 @escape [type NodeId]
93 @escape [type EdgeId]
94 @section nodelegate
95 type EdgeId: Copy + PartialEq;
97 type NodeId: Copy + PartialEq;
99}
100}
101
102GraphBase! {delegate_impl []}
103GraphBase! {delegate_impl [['a, G], G, &'a mut G, deref]}
104
105pub trait GraphRef: Copy + GraphBase {}
107
108impl<'a, G> GraphRef for &'a G where G: GraphBase {}
109
110impl<'a, G> GraphBase for Frozen<'a, G>
111where
112 G: GraphBase,
113{
114 type NodeId = G::NodeId;
115 type EdgeId = G::EdgeId;
116}
117
118#[cfg(feature = "stable_graph")]
119impl<'a, N, E: 'a, Ty, Ix> IntoNeighbors for &'a StableGraph<N, E, Ty, Ix>
120where
121 Ty: EdgeType,
122 Ix: IndexType,
123{
124 type Neighbors = stable_graph::Neighbors<'a, E, Ix>;
125 fn neighbors(self, n: Self::NodeId) -> Self::Neighbors {
126 (*self).neighbors(n)
127 }
128}
129
130#[cfg(feature = "graphmap")]
131impl<'a, N: 'a, E, Ty> IntoNeighbors for &'a GraphMap<N, E, Ty>
132where
133 N: Copy + Ord + Hash,
134 Ty: EdgeType,
135{
136 type Neighbors = graphmap::Neighbors<'a, N, Ty>;
137 fn neighbors(self, n: Self::NodeId) -> Self::Neighbors {
138 self.neighbors(n)
139 }
140}
141
142trait_template! {
143pub trait IntoNeighbors : GraphRef {
150 @section type
151 type Neighbors: Iterator<Item=Self::NodeId>;
152 @section self
153 fn neighbors(self: Self, a: Self::NodeId) -> Self::Neighbors;
155}
156}
157
158IntoNeighbors! {delegate_impl []}
159
160trait_template! {
161pub trait IntoNeighborsDirected : IntoNeighbors {
170 @section type
171 type NeighborsDirected: Iterator<Item=Self::NodeId>;
172 @section self
173 fn neighbors_directed(self, n: Self::NodeId, d: Direction)
174 -> Self::NeighborsDirected;
175}
176}
177
178impl<'a, N, E: 'a, Ty, Ix> IntoNeighbors for &'a Graph<N, E, Ty, Ix>
179where
180 Ty: EdgeType,
181 Ix: IndexType,
182{
183 type Neighbors = graph::Neighbors<'a, E, Ix>;
184 fn neighbors(self, n: graph::NodeIndex<Ix>) -> graph::Neighbors<'a, E, Ix> {
185 Graph::neighbors(self, n)
186 }
187}
188
189impl<'a, N, E: 'a, Ty, Ix> IntoNeighborsDirected for &'a Graph<N, E, Ty, Ix>
190where
191 Ty: EdgeType,
192 Ix: IndexType,
193{
194 type NeighborsDirected = graph::Neighbors<'a, E, Ix>;
195 fn neighbors_directed(
196 self,
197 n: graph::NodeIndex<Ix>,
198 d: Direction,
199 ) -> graph::Neighbors<'a, E, Ix> {
200 Graph::neighbors_directed(self, n, d)
201 }
202}
203
204#[cfg(feature = "stable_graph")]
205impl<'a, N, E: 'a, Ty, Ix> IntoNeighborsDirected for &'a StableGraph<N, E, Ty, Ix>
206where
207 Ty: EdgeType,
208 Ix: IndexType,
209{
210 type NeighborsDirected = stable_graph::Neighbors<'a, E, Ix>;
211 fn neighbors_directed(self, n: graph::NodeIndex<Ix>, d: Direction) -> Self::NeighborsDirected {
212 StableGraph::neighbors_directed(self, n, d)
213 }
214}
215
216#[cfg(feature = "graphmap")]
217impl<'a, N: 'a, E, Ty> IntoNeighborsDirected for &'a GraphMap<N, E, Ty>
218where
219 N: Copy + Ord + Hash,
220 Ty: EdgeType,
221{
222 type NeighborsDirected = graphmap::NeighborsDirected<'a, N, Ty>;
223 fn neighbors_directed(self, n: N, dir: Direction) -> Self::NeighborsDirected {
224 self.neighbors_directed(n, dir)
225 }
226}
227
228trait_template! {
229pub trait IntoEdges : IntoEdgeReferences + IntoNeighbors {
242 @section type
243 type Edges: Iterator<Item=Self::EdgeRef>;
244 @section self
245 fn edges(self, a: Self::NodeId) -> Self::Edges;
246}
247}
248
249IntoEdges! {delegate_impl []}
250
251trait_template! {
252pub trait IntoEdgesDirected : IntoEdges + IntoNeighborsDirected {
268 @section type
269 type EdgesDirected: Iterator<Item=Self::EdgeRef>;
270 @section self
271 fn edges_directed(self, a: Self::NodeId, dir: Direction) -> Self::EdgesDirected;
272}
273}
274
275IntoEdgesDirected! {delegate_impl []}
276
277trait_template! {
278pub trait IntoNodeIdentifiers : GraphRef {
280 @section type
281 type NodeIdentifiers: Iterator<Item=Self::NodeId>;
282 @section self
283 fn node_identifiers(self) -> Self::NodeIdentifiers;
284}
285}
286
287IntoNodeIdentifiers! {delegate_impl []}
288
289impl<'a, N, E: 'a, Ty, Ix> IntoNodeIdentifiers for &'a Graph<N, E, Ty, Ix>
290where
291 Ty: EdgeType,
292 Ix: IndexType,
293{
294 type NodeIdentifiers = graph::NodeIndices<Ix>;
295 fn node_identifiers(self) -> graph::NodeIndices<Ix> {
296 Graph::node_indices(self)
297 }
298}
299
300impl<N, E, Ty, Ix> NodeCount for Graph<N, E, Ty, Ix>
301where
302 Ty: EdgeType,
303 Ix: IndexType,
304{
305 fn node_count(&self) -> usize {
306 self.node_count()
307 }
308}
309
310#[cfg(feature = "stable_graph")]
311impl<'a, N, E: 'a, Ty, Ix> IntoNodeIdentifiers for &'a StableGraph<N, E, Ty, Ix>
312where
313 Ty: EdgeType,
314 Ix: IndexType,
315{
316 type NodeIdentifiers = stable_graph::NodeIndices<'a, N, Ix>;
317 fn node_identifiers(self) -> Self::NodeIdentifiers {
318 StableGraph::node_indices(self)
319 }
320}
321
322#[cfg(feature = "stable_graph")]
323impl<N, E, Ty, Ix> NodeCount for StableGraph<N, E, Ty, Ix>
324where
325 Ty: EdgeType,
326 Ix: IndexType,
327{
328 fn node_count(&self) -> usize {
329 self.node_count()
330 }
331}
332
333IntoNeighborsDirected! {delegate_impl []}
334
335trait_template! {
336pub trait Data : GraphBase {
338 @section type
339 type NodeWeight;
340 type EdgeWeight;
341}
342}
343
344Data! {delegate_impl []}
345Data! {delegate_impl [['a, G], G, &'a mut G, deref]}
346
347pub trait EdgeRef: Copy {
351 type NodeId;
352 type EdgeId;
353 type Weight;
354 fn source(&self) -> Self::NodeId;
356 fn target(&self) -> Self::NodeId;
358 fn weight(&self) -> &Self::Weight;
360 fn id(&self) -> Self::EdgeId;
362}
363
364impl<'a, N, E> EdgeRef for (N, N, &'a E)
365where
366 N: Copy,
367{
368 type NodeId = N;
369 type EdgeId = (N, N);
370 type Weight = E;
371
372 fn source(&self) -> N {
373 self.0
374 }
375 fn target(&self) -> N {
376 self.1
377 }
378 fn weight(&self) -> &E {
379 self.2
380 }
381 fn id(&self) -> (N, N) {
382 (self.0, self.1)
383 }
384}
385
386pub trait NodeRef: Copy {
388 type NodeId;
389 type Weight;
390 fn id(&self) -> Self::NodeId;
391 fn weight(&self) -> &Self::Weight;
392}
393
394trait_template! {
395pub trait IntoNodeReferences : Data + IntoNodeIdentifiers {
397 @section type
398 type NodeRef: NodeRef<NodeId=Self::NodeId, Weight=Self::NodeWeight>;
399 type NodeReferences: Iterator<Item=Self::NodeRef>;
400 @section self
401 fn node_references(self) -> Self::NodeReferences;
402}
403}
404
405IntoNodeReferences! {delegate_impl []}
406
407impl<Id> NodeRef for (Id, ())
408where
409 Id: Copy,
410{
411 type NodeId = Id;
412 type Weight = ();
413 fn id(&self) -> Self::NodeId {
414 self.0
415 }
416 fn weight(&self) -> &Self::Weight {
417 static DUMMY: () = ();
418 &DUMMY
419 }
420}
421
422impl<'a, Id, W> NodeRef for (Id, &'a W)
423where
424 Id: Copy,
425{
426 type NodeId = Id;
427 type Weight = W;
428 fn id(&self) -> Self::NodeId {
429 self.0
430 }
431 fn weight(&self) -> &Self::Weight {
432 self.1
433 }
434}
435
436trait_template! {
437pub trait IntoEdgeReferences : Data + GraphRef {
439 @section type
440 type EdgeRef: EdgeRef<NodeId=Self::NodeId, EdgeId=Self::EdgeId,
441 Weight=Self::EdgeWeight>;
442 type EdgeReferences: Iterator<Item=Self::EdgeRef>;
443 @section self
444 fn edge_references(self) -> Self::EdgeReferences;
445}
446}
447
448IntoEdgeReferences! {delegate_impl [] }
449
450#[cfg(feature = "graphmap")]
451impl<N, E, Ty> Data for GraphMap<N, E, Ty>
452where
453 N: Copy + PartialEq,
454 Ty: EdgeType,
455{
456 type NodeWeight = N;
457 type EdgeWeight = E;
458}
459
460trait_template! {
461 pub trait GraphProp : GraphBase {
463 @section type
464 type EdgeType: EdgeType;
466
467 @section nodelegate
468 fn is_directed(&self) -> bool {
469 <Self::EdgeType>::is_directed()
470 }
471}
472}
473
474GraphProp! {delegate_impl []}
475
476impl<N, E, Ty, Ix> GraphProp for Graph<N, E, Ty, Ix>
477where
478 Ty: EdgeType,
479 Ix: IndexType,
480{
481 type EdgeType = Ty;
482}
483
484#[cfg(feature = "stable_graph")]
485impl<N, E, Ty, Ix> GraphProp for StableGraph<N, E, Ty, Ix>
486where
487 Ty: EdgeType,
488 Ix: IndexType,
489{
490 type EdgeType = Ty;
491}
492
493#[cfg(feature = "graphmap")]
494impl<N, E, Ty> GraphProp for GraphMap<N, E, Ty>
495where
496 N: NodeTrait,
497 Ty: EdgeType,
498{
499 type EdgeType = Ty;
500}
501
502impl<'a, N: 'a, E: 'a, Ty, Ix> IntoEdgeReferences for &'a Graph<N, E, Ty, Ix>
503where
504 Ty: EdgeType,
505 Ix: IndexType,
506{
507 type EdgeRef = graph::EdgeReference<'a, E, Ix>;
508 type EdgeReferences = graph::EdgeReferences<'a, E, Ix>;
509 fn edge_references(self) -> Self::EdgeReferences {
510 (*self).edge_references()
511 }
512}
513
514trait_template! {
515 pub trait NodeIndexable : GraphBase {
517 @section self
518 fn node_bound(self: &Self) -> usize;
521 fn to_index(self: &Self, a: Self::NodeId) -> usize;
523 fn from_index(self: &Self, i: usize) -> Self::NodeId;
525 }
526}
527
528NodeIndexable! {delegate_impl []}
529
530trait_template! {
531pub trait NodeCount : GraphBase {
533 @section self
534 fn node_count(self: &Self) -> usize;
535}
536}
537
538NodeCount! {delegate_impl []}
539
540trait_template! {
541pub trait NodeCompactIndexable : NodeIndexable + NodeCount { }
546}
547
548NodeCompactIndexable! {delegate_impl []}
549
550impl<N, E, Ty, Ix> NodeIndexable for Graph<N, E, Ty, Ix>
551where
552 Ty: EdgeType,
553 Ix: IndexType,
554{
555 #[inline]
556 fn node_bound(&self) -> usize {
557 self.node_count()
558 }
559 #[inline]
560 fn to_index(&self, ix: NodeIndex<Ix>) -> usize {
561 ix.index()
562 }
563 #[inline]
564 fn from_index(&self, ix: usize) -> Self::NodeId {
565 NodeIndex::new(ix)
566 }
567}
568
569impl<N, E, Ty, Ix> NodeCompactIndexable for Graph<N, E, Ty, Ix>
570where
571 Ty: EdgeType,
572 Ix: IndexType,
573{
574}
575
576pub trait VisitMap<N> {
578 fn visit(&mut self, a: N) -> bool;
582
583 fn is_visited(&self, a: &N) -> bool;
585}
586
587impl<Ix> VisitMap<Ix> for FixedBitSet
588where
589 Ix: IndexType,
590{
591 fn visit(&mut self, x: Ix) -> bool {
592 !self.put(x.index())
593 }
594 fn is_visited(&self, x: &Ix) -> bool {
595 self.contains(x.index())
596 }
597}
598
599#[cfg(feature = "std")]
600impl<N, S> VisitMap<N> for HashSet<N, S>
601where
602 N: Hash + Eq,
603 S: BuildHasher,
604{
605 fn visit(&mut self, x: N) -> bool {
606 self.insert(x)
607 }
608 fn is_visited(&self, x: &N) -> bool {
609 self.contains(x)
610 }
611}
612
613#[cfg(not(feature = "std"))]
614impl<N> VisitMap<N> for HashSet<N>
615where
616 N: Ord + Eq,
617{
618 fn visit(&mut self, x: N) -> bool {
619 self.insert(x)
620 }
621 fn is_visited(&self, x: &N) -> bool {
622 self.contains(x)
623 }
624}
625
626trait_template! {
627pub trait Visitable : GraphBase {
629 @section type
630 type Map: VisitMap<Self::NodeId>;
632 @section self
633 fn visit_map(self: &Self) -> Self::Map;
635 fn reset_map(self: &Self, map: &mut Self::Map);
637}
638}
639Visitable! {delegate_impl []}
640
641impl<N, E, Ty, Ix> GraphBase for Graph<N, E, Ty, Ix>
642where
643 Ix: IndexType,
644{
645 type NodeId = graph::NodeIndex<Ix>;
646 type EdgeId = graph::EdgeIndex<Ix>;
647}
648
649impl<N, E, Ty, Ix> Visitable for Graph<N, E, Ty, Ix>
650where
651 Ty: EdgeType,
652 Ix: IndexType,
653{
654 type Map = FixedBitSet;
655 fn visit_map(&self) -> FixedBitSet {
656 FixedBitSet::with_capacity(self.node_count())
657 }
658
659 fn reset_map(&self, map: &mut Self::Map) {
660 map.clear();
661 map.grow(self.node_count());
662 }
663}
664
665#[cfg(feature = "stable_graph")]
666impl<N, E, Ty, Ix> GraphBase for StableGraph<N, E, Ty, Ix>
667where
668 Ix: IndexType,
669{
670 type NodeId = graph::NodeIndex<Ix>;
671 type EdgeId = graph::EdgeIndex<Ix>;
672}
673
674#[cfg(feature = "stable_graph")]
675impl<N, E, Ty, Ix> Visitable for StableGraph<N, E, Ty, Ix>
676where
677 Ty: EdgeType,
678 Ix: IndexType,
679{
680 type Map = FixedBitSet;
681 fn visit_map(&self) -> FixedBitSet {
682 FixedBitSet::with_capacity(self.node_bound())
683 }
684 fn reset_map(&self, map: &mut Self::Map) {
685 map.clear();
686 map.grow(self.node_bound());
687 }
688}
689
690#[cfg(feature = "stable_graph")]
691impl<N, E, Ty, Ix> Data for StableGraph<N, E, Ty, Ix>
692where
693 Ty: EdgeType,
694 Ix: IndexType,
695{
696 type NodeWeight = N;
697 type EdgeWeight = E;
698}
699
700#[cfg(feature = "graphmap")]
701impl<N, E, Ty> GraphBase for GraphMap<N, E, Ty>
702where
703 N: Copy + PartialEq,
704{
705 type NodeId = N;
706 type EdgeId = (N, N);
707}
708
709#[cfg(feature = "graphmap")]
710impl<N, E, Ty> Visitable for GraphMap<N, E, Ty>
711where
712 N: Copy + Ord + Hash,
713 Ty: EdgeType,
714{
715 type Map = HashSet<N>;
716 fn visit_map(&self) -> HashSet<N> {
717 HashSet::new()
718 }
719 fn reset_map(&self, map: &mut Self::Map) {
720 map.clear();
721 }
722}
723
724trait_template! {
725pub trait GetAdjacencyMatrix : GraphBase {
730 @section type
731 type AdjMatrix;
733 @section self
734 fn adjacency_matrix(self: &Self) -> Self::AdjMatrix;
736 fn is_adjacent(self: &Self, matrix: &Self::AdjMatrix, a: Self::NodeId, b: Self::NodeId) -> bool;
740}
741}
742
743GetAdjacencyMatrix! {delegate_impl []}
744
745#[cfg(feature = "graphmap")]
746impl<N, E, Ty> GetAdjacencyMatrix for GraphMap<N, E, Ty>
748where
749 N: Copy + Ord + Hash,
750 Ty: EdgeType,
751{
752 type AdjMatrix = ();
753 #[inline]
754 fn adjacency_matrix(&self) {}
755 #[inline]
756 fn is_adjacent(&self, _: &(), a: N, b: N) -> bool {
757 self.contains_edge(a, b)
758 }
759}
760
761trait_template! {
762pub trait EdgeCount : GraphBase {
764 @section self
765 fn edge_count(self: &Self) -> usize;
767}
768}
769
770EdgeCount! {delegate_impl []}
771
772impl<N, E, Ty, Ix> EdgeCount for Graph<N, E, Ty, Ix>
773where
774 Ty: EdgeType,
775 Ix: IndexType,
776{
777 #[inline]
778 fn edge_count(&self) -> usize {
779 self.edge_count()
780 }
781}
782
783#[cfg(feature = "stable_graph")]
784impl<N, E, Ty, Ix> EdgeCount for StableGraph<N, E, Ty, Ix>
785where
786 Ty: EdgeType,
787 Ix: IndexType,
788{
789 #[inline]
790 fn edge_count(&self) -> usize {
791 self.edge_count()
792 }
793}
794
795#[cfg(feature = "graphmap")]
796impl<N, E, Ty> EdgeCount for GraphMap<N, E, Ty>
797where
798 N: NodeTrait,
799 Ty: EdgeType,
800{
801 #[inline]
802 fn edge_count(&self) -> usize {
803 self.edge_count()
804 }
805}
806
807#[cfg(feature = "matrix_graph")]
808impl<N, E, Ty> EdgeCount for MatrixGraph<N, E, Ty>
809where
810 N: NodeTrait,
811 Ty: EdgeType,
812{
813 #[inline]
814 fn edge_count(&self) -> usize {
815 self.edge_count()
816 }
817}
818
819impl<N, E, Ty, Ix> EdgeCount for Csr<N, E, Ty, Ix>
820where
821 Ty: EdgeType,
822 Ix: IndexType,
823{
824 #[inline]
825 fn edge_count(&self) -> usize {
826 self.edge_count()
827 }
828}
829
830mod filter;
831mod reversed;