/// <summary> /// Recursive procedure to identify sequence cuts. /// </summary> /// <param name="graphNode">Analyzed node</param> /// <author>Krystian Zielonka, Bernd Nottbeck</author> private HashSet <InductiveMinerRow> SequenceCutHelper(InductiveMinerGraphNode graphNode) { HashSet <InductiveMinerRow> sequenceList = new HashSet <InductiveMinerRow>(); if (!visitedNodes.Contains(graphNode)) { visitedNodes.Add(graphNode); List <InductiveMinerRow> followerList = graphNode.FollowerList; foreach (InductiveMinerRow row in followerList) { var query = from SearchRow in row.ToNode.EventualFollowerList where SearchRow.ToNode == row.FromNode select SearchRow; InductiveMinerRow currentRow = query.FirstOrDefault(); if (currentRow == null && !graphNode.Name.Equals(startEvent) && !graphNode.Name.Equals(newStart)) { sequenceList.Add(row); } sequenceList.UnionWith(SequenceCutHelper(row.ToNode)); } } return(sequenceList); }
/// <summary> /// Executes the last cut in a loop /// </summary> /// <param name="LoopStart">Loop start node</param> /// <param name="currentNode">Analysed node</param> /// <returns>true if cut was made</returns> private bool executeLastCutInLoop(InductiveMinerGraphNode LoopStart, InductiveMinerGraphNode currentNode) { if (currentNode.FollowerList.Count > 0) { if (currentNode.GetMyDirectNodes().Contains(LoopStart)) { var query = from search in currentNode.FollowerList where search.ToNode == LoopStart select search; InductiveMinerRow deleteRow = query.FirstOrDefault(); currentNode.FollowerList.Remove(deleteRow); return(true); } else { foreach (InductiveMinerRow row in currentNode.FollowerList) { if (executeLastCutInLoop(LoopStart, row.ToNode)) { return(true); } } } } return(false); }
/// <summary> /// Eliminates infrequent directly follower /// </summary> /// <author>Bernd Nottbeck</author> public void EliminateInfrequent() { if (FollowerList.Count > 1) { InductiveMinerRow lastRow = FollowerList.Last <InductiveMinerRow>(); int ThreshHoldValue = (int)Math.Round(lastRow.Count * threshHold); bool SomethingWasRemoved = true; List <InductiveMinerRow> .Enumerator e = FollowerList.GetEnumerator(); List <InductiveMinerRow> deleteList = new List <InductiveMinerRow>(); e.MoveNext(); do { if (e.Current.Count < ThreshHoldValue) { deleteList.Add(e.Current); } else { SomethingWasRemoved = false; } if (!e.MoveNext()) { SomethingWasRemoved = false; } } while (SomethingWasRemoved); e.Dispose(); foreach (InductiveMinerRow deleteRow in deleteList) { FollowerList.Remove(deleteRow); } } }
/// <summary> /// Recursive procedure to identify loop cuts /// </summary> /// <param name="graphNode">Analyzed node</param> /// <author>Krystian Zielonka, Bernd Nottbeck</author> private bool CheckLoopCut(InductiveMinerGraphNode graphNode) { bool foundSth = false; if (!visitedLoopCheckNodes.Contains(graphNode)) { visitedLoopCheckNodes.Add(graphNode); List <InductiveMinerRow> followerList = graphNode.FollowerList; foreach (InductiveMinerRow row in followerList) { var query = from SearchRow in row.ToNode.EventualFollowerList where SearchRow.ToNode == row.FromNode select SearchRow; InductiveMinerRow currentRow = query.FirstOrDefault(); bool and = false; if (currentRow != null) { foreach (InductiveMinerGraphNode andCheckNode in currentRow.FromNode.GetMyDirectNodes()) { if (andCheckNode.GetMyDirectNodes().Contains(currentRow.FromNode)) { and = true; } } } if (currentRow != null && !and) { foundSth = true; bool cutFound = executeLastCutInLoop(row.FromNode, row.ToNode); if (cutFound) { executeFirstCutInLoop(row.FromNode, row.ToNode); return(true); } } if (foundSth) { } else { if (CheckLoopCut(row.ToNode)) { return(true); } } } } return(foundSth); }
/// <summary> /// Identifies a Sequence cut /// </summary> /// <returns>True if cut was made</returns> private bool CheckSequenceCut() { HashSet <InductiveMinerRow> sequenceList = SequenceCutHelper(GraphNode); bool isSequence = sequenceList.Any(); if (isSequence) { int middle = IsEven(sequenceList.Count) ? (sequenceList.Count - 1) / 2 : sequenceList.Count / 2; InductiveMinerRow middleRow = sequenceList.ElementAt(middle); List <InductiveMinerRow> sequenceNodes = sequenceList.Where(k => k.FromNode.Equals(middleRow.FromNode) || k.ToNode.Equals(middleRow.ToNode)).ToList(); var fromNodeQuery = from row in sequenceNodes where row.FromNode != middleRow.FromNode select row.FromNode; var toNodeQuery = from row in sequenceNodes where row.ToNode != middleRow.ToNode select row.ToNode; List <InductiveMinerGraphNode> fromNodes = fromNodeQuery.ToList(); List <InductiveMinerGraphNode> toNodes = toNodeQuery.ToList(); sequenceNodes.AddRange(sequenceList.Where(k => fromNodes.Contains(k.FromNode) && toNodes.Contains(k.ToNode)).ToList()); sequenceList = new HashSet <InductiveMinerRow>(sequenceNodes); foreach (InductiveMinerRow sequenceRow in sequenceList) { newStart.AddDirectFollower(sequenceRow.ToNode); foreach (InductiveMinerGraphNode eventllyNode in sequenceRow.ToNode.GetMyEventualNodes()) { newStart.AddEventualFollower(eventllyNode); } sequenceRow.FromNode.WasCut = true; sequenceRow.FromNode.DeleteFollower(sequenceRow); sequenceRow.FromNode.ReBuildeEventualFollower(null); sequenceRow.FromNode.CleanUpHelperList(null); } newStart.ReBuildeEventualFollower(null); newStart.CleanUpHelperList(null); } return(isSequence); }
/// <summary> /// Identifies parallels in the graph /// </summary> /// <param name="graphNode">Analyzed node</param> /// <author>Krystian Zielonka, Thomas Meents, Bernd Nottbeck</author> private bool CheckAndCut(InductiveMinerGraphNode graphNode) { bool wasSplit = false; if (graphNode.FollowerList.Count > 1) { List <InductiveMinerRow> followerList = graphNode.FollowerList; List <InductiveMinerRow> deleteList = new List <InductiveMinerRow>(); foreach (InductiveMinerRow row in followerList) { InductiveMinerRow currentRow = row.ToNode.FollowerList.FirstOrDefault(); if (currentRow.ToNode.GetMyDirectNodes().Contains(currentRow.FromNode)) { deleteList.Add(currentRow); } } wasSplit = deleteList.Any(); if (wasSplit) { foreach (InductiveMinerRow row in deleteList) { row.FromNode.DeleteFollower(row); } InductiveMinerRow lastRow = deleteList.Last(); newStart.AddDirectFollower(lastRow.FromNode); newStart.AddEventualFollower(lastRow.FromNode); graphNode.DeleteFollower(graphNode.GetRowWithFollower(lastRow.FromNode)); graphNode.ReBuildeEventualFollower(null); graphNode.CleanUpHelperList(null); } } return(wasSplit); }
public void DeleteFollower(InductiveMinerRow rowToDelete) { FollowerList.Remove(rowToDelete); }