public void Traverse(IEnumerable <TDependency> dependencies, ItemMatch pathAnchor, bool pathAnchorIsCountMatch, AbstractPathMatch <TDependency, TItem>[] expectedPathMatches) { Dictionary <TItem, TDependency[]> incidentDependencies = _backwards ? AbstractItem <TItem> .CollectIncomingDependenciesMap(dependencies) : AbstractItem <TItem> .CollectOutgoingDependenciesMap(dependencies); _seenInnerPathStarts.Clear(); Paths.Clear(); Counts.Clear(); _onPath.Clear(); TItem[] uniqueStartItems = (pathAnchor == null ? incidentDependencies.Keys : incidentDependencies.Keys.Where(i => pathAnchor.Matches(i).Success)).ToArray(); AbstractPathMatch <TDependency, TItem> endMatch; AbstractPathMatch <TDependency, TItem>[] innerMatches; int n = expectedPathMatches.Length; if (n == 0) { endMatch = null; innerMatches = expectedPathMatches; } else { endMatch = expectedPathMatches[n - 1]; innerMatches = expectedPathMatches.Take(n - 1).ToArray(); } foreach (var item in uniqueStartItems.OrderBy(i => i.Name)) { if (_seenInnerPathStarts.Add(item)) { List <PathNode <TItem, TDependency> > up = Traverse(root: item, incidentDependencies: incidentDependencies, expectedInnerPathMatches: innerMatches, endMatch: endMatch, down: new DownInfo(pathAnchorIsCountMatch ? item : null)); if (up != null) { Paths.Add(item, up); } } } }
public FindCycleDepsPathFinder([NotNull, ItemNotNull] IEnumerable <TDependency> dependencies, [CanBeNull] ItemMatch cycleAnchorsMatch, bool ignoreSelfCycles, int maxCycleLength, [NotNull] Action <int, Stack <TDependency>, string> recordNewCycleToRoot, [NotNull, ItemCanBeNull] AbstractPathMatch <TDependency, TItem>[] expectedPathMatches, Action checkAbort) : base(checkAbort) { Dictionary <TItem, TDependency[]> outgoing = AbstractItem <TItem> .CollectOutgoingDependenciesMap(dependencies); _maxCycleLength = maxCycleLength; _ignoreSelfCycles = ignoreSelfCycles; _recordNewCycleToRoot = recordNewCycleToRoot; IEnumerable <TItem> roots = outgoing.Keys.Where(i => ItemMatch.IsMatch(cycleAnchorsMatch, i)); _addIndexToMarkerFormat = "D" + ("" + roots.Count() / 2).Length; foreach (var root in roots.OrderBy(i => i.Name)) { _root = root; _visited2RestLength = new Dictionary <TItem, int>(); Traverse(root, outgoing, expectedPathMatches, endMatch: null, down: Ignore.Om); } }