private LabyrinthElement SearchForEmptyElementToProccess(LabyrinthElement elementToCheck, List <LabyrinthElement> checkedElements) { checkedElements.Add(elementToCheck); if (elementToCheck.Type == ElementType.Empty && !elementToCheck.Proccessed) { return(elementToCheck); } foreach (var closeElement in elementToCheck.CloseElements) { if (checkedElements.Any(e => e.Point.X == closeElement.Point.X && e.Point.Y == closeElement.Point.Y)) { continue; } if (closeElement.Type != ElementType.Wall) { if (closeElement.Proccessed) { var result = SearchForEmptyElementToProccess(closeElement, checkedElements); if (result != null) { return(result); } } else { return(closeElement); } } } return(null); }
private void SearchPathToProccessedElement(LabyrinthElement currentElement, Point pointToGetTo, LabyrinthElementChain parentChain, List <LabyrinthElementChain> foundChains) { if (parentChain == null) { parentChain = new LabyrinthElementChain(currentElement); } else { parentChain = new LabyrinthElementChain(currentElement, parentChain); } foreach (var elementToCheck in currentElement.CloseElements.Where(e => e.Type != ElementType.Wall)) { if (GetChainElements(parentChain).Any(e => e.Point.X == elementToCheck.Point.X && e.Point.Y == elementToCheck.Point.Y)) { continue; } if (elementToCheck.Point.X == pointToGetTo.X && elementToCheck.Point.Y == pointToGetTo.Y) { foundChains.Add(new LabyrinthElementChain(elementToCheck, parentChain)); } else { SearchPathToProccessedElement(elementToCheck, pointToGetTo, parentChain, foundChains); } } }
private void DrawElement(LabyrinthElement element) { var elementText = string.Empty; switch (element.Type) { case ElementType.Empty: elementText = " "; break; case ElementType.Start: elementText = "S"; break; case ElementType.Finish: elementText = "F"; break; case ElementType.Wall: elementText = "#"; break; } var labyrinthUIElement = new LabyrinthUIElement { Type = element.Type, Point = new Point(element.Point.X, element.Point.Y), TextBlock = new TextBlock { Text = elementText, FontSize = 22 } }; _elements.Add(labyrinthUIElement); Canvas.SetLeft(labyrinthUIElement.TextBlock, element.Point.X * 20); Canvas.SetBottom(labyrinthUIElement.TextBlock, element.Point.Y * 20); _canvas.Children.Add(labyrinthUIElement.TextBlock); }
private void ProcessLabyrinth(LabyrinthElement elementToProccess, List <LabyrinthElement> proccessedElements, List <LabyrinthElement> existingElements) { if (_finishFound) { return; } var x = elementToProccess.Point.X; var y = elementToProccess.Point.Y; Thread.Sleep(80); OnStepChanged(new StepChangeEventArgs(elementToProccess.Point)); var closeElements = existingElements.Where(e => (e.Point.X == x - 1 && e.Point.Y == y) || (e.Point.X == x + 1 && e.Point.Y == y) || (e.Point.X == x && e.Point.Y == y + 1) || (e.Point.X == x && e.Point.Y == y - 1)) .Where(e => !elementToProccess.CloseElements.Any(c => c.Equals(e))).ToList(); elementToProccess.CloseElements.AddRange(closeElements); foreach (var closeElement in elementToProccess.CloseElements) { if (!closeElement.CloseElements.Any(e => e.Equals(elementToProccess))) { closeElement.CloseElements.Add(elementToProccess); } } elementToProccess.Proccessed = true; proccessedElements.Add(elementToProccess); if (elementToProccess.Type == ElementType.Finish) { _finishFound = true; return; } var closestFinishElement = elementToProccess.CloseElements.FirstOrDefault(e => e.Type == ElementType.Finish); if (closestFinishElement != null) { ProcessLabyrinth(closestFinishElement, proccessedElements, existingElements); } var closestNotProccessedEmptyElement = elementToProccess.CloseElements.FirstOrDefault(e => e.Type == ElementType.Empty && !e.Proccessed); if (closestNotProccessedEmptyElement != null) { ProcessLabyrinth(closestNotProccessedEmptyElement, proccessedElements, existingElements); } var elemntsListChecked = new List <LabyrinthElement>(); var emptyNotProccessedElement = SearchForEmptyElementToProccess(elementToProccess, elemntsListChecked); if (emptyNotProccessedElement == null) { return; } var chains = new List <LabyrinthElementChain>(); SearchPathToProccessedElement(elementToProccess, emptyNotProccessedElement.Point, null, chains); var chainElements = GetChainElements(chains.FirstOrDefault()); chainElements.Reverse(); foreach (var element in chainElements) { if (_finishFound) { break; } Thread.Sleep(80); OnStepChanged(new StepChangeEventArgs(element.Point)); } ProcessLabyrinth(emptyNotProccessedElement, proccessedElements, existingElements); }
private void GoToNotProccessedElement(LabyrinthElement currentElement, LabyrinthElement elementToGetTo, List <LabyrinthElement> existingElements) { }
public LabyrinthElementChain(LabyrinthElement element) { LabyrinthElement = element; }
public LabyrinthElementChain(LabyrinthElement element, LabyrinthElementChain parent) { LabyrinthElement = element; Parent = parent; }
public static LabyrinthModel ParseLabyrinthFile() { var location = new Uri(Assembly.GetEntryAssembly().GetName().CodeBase); var directory = new FileInfo(location.AbsolutePath).Directory.FullName; var filePath = $"{directory}\\{AppSettings.Default.LabyrinthFileName}"; if (!File.Exists(filePath)) { throw new Exception("File not exists."); } var linesList = File.ReadAllLines(filePath).Reverse().ToList(); var model = new LabyrinthModel(); short lineNumber = 0; foreach (var line in linesList) { short charNumber = 0; foreach (var character in line) { var element = new LabyrinthElement { Point = new Point(charNumber, lineNumber) }; switch (character) { case ' ': element.Type = ElementType.Empty; break; case 'S': element.Type = ElementType.Start; break; case 'F': element.Type = ElementType.Finish; break; case '#': element.Type = ElementType.Wall; break; default: throw new Exception($"Input file contains unexpected character '{character}'"); } model.Elements.Add(element); charNumber++; } lineNumber++; } var startPoint = model.Elements.FirstOrDefault(e => e.Type == ElementType.Start); if (startPoint == null) { throw new Exception("Start point not exists in input file."); } var finishPoint = model.Elements.FirstOrDefault(e => e.Type == ElementType.Finish); if (finishPoint == null) { throw new Exception("Finish point not exists in input file."); } return(model); }