コード例 #1
0
        public ConsoleColor GetCellColor(GridPoint point)
        {
            if (!Maze.MazeCells.ContainsKey(point))
            {
                return(Console.ForegroundColor);
            }

            var cell = Maze.MazeCells[point];

            if (MazeCellType.Wall.Equals(cell.Type))
            {
                return(ConsoleColor.DarkGray);
            }
            if (Maze.CellsWithDoors.ContainsKey(point) &&
                !KeysCollected.ContainsKey(Maze.CellsWithDoors[point].ToLower()))
            {
                return(ConsoleColor.Red);
            }
            if (Maze.CellsWithKeys.ContainsKey(point) &&
                !KeysCollected.ContainsKey(Maze.CellsWithKeys[point]))
            {
                return(ConsoleColor.Cyan);
            }
            if (CurrentPositions.Contains(point))
            {
                return(ConsoleColor.Green);
            }
            return(Console.ForegroundColor);
        }
コード例 #2
0
        public string GetCellString(GridPoint point)
        {
            if (!Maze.MazeCells.ContainsKey(point))
            {
                return(" ");
            }

            var cell = Maze.MazeCells[point];

            if (MazeCellType.Wall.Equals(cell.Type))
            {
                return("#");
            }
            if (Maze.CellsWithDoors.ContainsKey(point) &&
                !KeysCollected.ContainsKey(Maze.CellsWithDoors[point].ToLower()))
            {
                return(Maze.CellsWithDoors[point]);
            }
            if (Maze.CellsWithKeys.ContainsKey(point) &&
                !KeysCollected.ContainsKey(Maze.CellsWithKeys[point]))
            {
                return(Maze.CellsWithKeys[point]);
            }
            if (CurrentPositions.Contains(point))
            {
                return("@");
            }
            return(".");
        }
コード例 #3
0
        public override bool Equals(object obj)
        {
            if (!(obj is State item))
            {
                return(false);
            }

            return(KeysCollected.Count == item.KeysCollected.Count && !KeysCollected.Except(item.KeysCollected).Any());
        }
コード例 #4
0
        public override bool Equals(object obj)
        {
            if (!(obj is BigState item))
            {
                return(false);
            }

            return(KeysCollected.Count == item.KeysCollected.Count && !KeysCollected.Except(item.KeysCollected).Any() &&
                   CurrentPositions.Count == item.CurrentPositions.Count);
        }
コード例 #5
0
        private string GetMazeStateSignature()
        {
            var signatureBuilder = new StringBuilder();

            if (KeysCollected.Count < Maze.Keys.Count)
            {
                foreach (var currentPosition in CurrentPositions)
                {
                    if (Maze.CellsWithKeys.ContainsKey(currentPosition))
                    {
                        signatureBuilder.Append(Maze.CellsWithKeys[currentPosition]);
                    }
                    else
                    {
                        signatureBuilder.Append("@");
                    }
                }
            }
            signatureBuilder.Append(":");
            signatureBuilder.Append(string.Join("", KeysCollected.Select(kvp => kvp.Key)));
            return(signatureBuilder.ToString());
        }
コード例 #6
0
        /// <summary>
        /// Retrieves all neighboring maze states that can be reached by moving
        /// the given position.
        /// </summary>
        /// <param name="positionIndex"></param>
        /// <returns></returns>
        private IList <Tuple <MazeState, int, int> > GetNeighboringMazeStatesWithCostsForPosition(int positionIndex)
        {
            var result          = new List <Tuple <MazeState, int, int> >();
            var currentPosition = CurrentPositions[positionIndex];

            foreach (var targetKey in Maze.Keys)
            {
                if (KeysCollected.ContainsKey(targetKey))
                {
                    continue;
                }

                var targetKeyCell = Maze.KeyCells[targetKey];

                // SIMPLIFYING ASSUMPTION:
                // The shortest paths between all pairs of keys when ignoring
                // doors always yields the ultimate shortest path
                var edgeKey = new Tuple <GridPoint, GridPoint>(currentPosition, targetKeyCell);
                if (!Maze.ShortestPathsBetweenKeysIgnoringDoors.ContainsKey(edgeKey))
                {
                    continue;
                }
                bool canReachTarget = true;
                foreach (var door in Maze.DoorsAlongShortestPathBetweenKeys[edgeKey])
                {
                    if (!KeysCollected.ContainsKey(door.ToLower()))
                    {
                        canReachTarget = false;
                    }
                }
                if (!canReachTarget)
                {
                    continue;
                }
                var shortestPath           = Maze.ShortestPathsBetweenKeysIgnoringDoors[edgeKey];
                var totalCost              = shortestPath.Count - 1;
                var keysCollectedAlongPath = Maze.GetKeysAlongPath(shortestPath);

                //// THIS CODE WORKS IN THE GENERAL CASE WHEN THE SIMPLIFYING ASSUMPTION IS NOT MET
                //int Heuristic(GridPoint currentCell)
                //{
                //    return GridPoint.GetManhattanDistance(currentCell, targetKeyCell);
                //}
                //bool GetCanEnterNode(GridPoint point)
                //{
                //    return Maze.GetCanEnterCell(point, KeysCollected);
                //}
                //var nodePathToTargetKeyCell = Maze.MazeGraph.GetShortestPathViaNodes(
                //    start: currentPosition,
                //    end: targetKeyCell,
                //    Heuristic: Heuristic,
                //    GetCanEnterNode: GetCanEnterNode);
                //if (nodePathToTargetKeyCell.Path.Count == 0)
                //    continue;
                //var keysCollectedAlongPath = Maze.GetKeysCollectedAlongNodePath(nodePathToTargetKeyCell.Path);
                //var shortestPath = Maze.GetRobotPathFromNodePath(nodePathToTargetKeyCell.Path);
                //var totalCost = shortestPath.Count - 1;

                var endKeysCollected = new SortedDictionary <string, string>(KeysCollected);
                foreach (var key in keysCollectedAlongPath)
                {
                    if (!endKeysCollected.ContainsKey(key))
                    {
                        endKeysCollected.Add(key, key);
                    }
                }
                var finalPositions = CurrentPositions.ToList();
                finalPositions[positionIndex] = targetKeyCell;
                var newMazeState = new MazeState(
                    maze: Maze,
                    currentPositions: finalPositions,
                    keysCollected: endKeysCollected);
                var resultEntry = new Tuple <MazeState, int, int>(
                    newMazeState,
                    totalCost,
                    positionIndex);
                result.Add(resultEntry);
            }
            return(result);
        }