private static LinkedList <BiMatchedLines> FindBidirectionalMapping(List <ExtendedLineInfo> mappingForLines1, List <ExtendedLineInfo> mappingForLines2) { Func <ExtendedLineInfo, Boolean, BiMatchedLines> bfsSearch = delegate(ExtendedLineInfo lineInfo, Boolean isInFirstList) { // first value in tuple: the index of the line in respective list; second value: true -> list1, false -> list2 var bfsList = new Queue <Tuple <ExtendedLineInfo, bool> > (); BiMatchedLines bimatchedLines = new BiMatchedLines(); // all matching lines that are meant to be together are a connected component in the bipartite graph of lines in list1 and list2 -> find // these with breadth-first search bfsList.Enqueue(new Tuple <ExtendedLineInfo, bool>(lineInfo, isInFirstList)); while (bfsList.Count > 0) { Tuple <ExtendedLineInfo, Boolean> currentTuple = bfsList.Dequeue(); ExtendedLineInfo currentLineInfo = currentTuple.Item1; // this value was already handled so it can be skipped if (currentLineInfo.alreadyUsedInBidirectionalSearch) { continue; } currentLineInfo.alreadyUsedInBidirectionalSearch = true; bimatchedLines.listlines[currentTuple.Item2 ? 0 : 1].AddLast(currentLineInfo.lineInfo); foreach (var oppositeLineMatching in currentLineInfo.matchingLines) { bfsList.Enqueue(new Tuple <ExtendedLineInfo, bool> (oppositeLineMatching, !currentTuple.Item2)); // this line is in the opposite list } } return((bimatchedLines.listlines[0].Count > 0 || bimatchedLines.listlines[1].Count > 0) ? bimatchedLines : null); }; var returnList = new LinkedList <BiMatchedLines> (); // handle all lines in list1 foreach (ExtendedLineInfo line in mappingForLines1) { BiMatchedLines bml = bfsSearch(line, true); if (bml != null) { returnList.AddLast(bml); } } // handle all lines in list2 foreach (ExtendedLineInfo line in mappingForLines2) { BiMatchedLines bml = bfsSearch(line, false); if (bml != null) { returnList.AddLast(bml); } } return(returnList); }
/// <summary> /// Returns the line from "matching lines" that has the least overlapping rating with "lineInfo". /// </summary> private static ExtendedLineInfo GetLeastFittingLine(LineInfo lineInfo, LinkedList <ExtendedLineInfo> matchingLines) { double leastFittingOverlappingScore = 0.5; ExtendedLineInfo leastFittingLine = null; foreach (ExtendedLineInfo matchingLine in matchingLines) { double currentOverlappingScore = UtilsCommon.OverlappingScore(lineInfo, matchingLine); if (leastFittingLine == null || (currentOverlappingScore < leastFittingOverlappingScore)) { leastFittingOverlappingScore = currentOverlappingScore; leastFittingLine = matchingLine; } } return(leastFittingLine); }