예제 #1
0
        public override Dictionary <QFeature, decimal> GetFeatures(QAction action)
        {
            Point              self       = ((Maze_With_No_Walls)GetNewState(action)).self;
            QSearch            qsearch    = new QSearch(this);
            Maze_With_No_Walls simpleMaze = new Maze_With_No_Walls()
            {
                maze = maze, self = self, goal = goal, width = width, height = height
            };
            QSearchResult bestPath = qsearch.AStar(simpleMaze);

            return(QFeature_String.FromStringDecimalDictionary(new Dictionary <string, decimal>()
            {
                //{this.GetHashCode().ToString()+"_"+action, 1}, // Identity to convert this back to QLearning
                { "Goal", goal == self? 1:0 },
                { "Distance_To_Goal", bestPath == null? 1:(decimal)bestPath.Count / (decimal)(width * height) },
            }));
        }
예제 #2
0
        public override Dictionary <QFeature, decimal> GetFeatures(QAction action)
        {
            int newVal = value;

            if (action == UP)
            {
                newVal++;
            }
            else
            {
                newVal--;
            }
            return(QFeature_String.FromStringDecimalDictionary(new Dictionary <string, decimal>()
            {
                //{value.ToString()+"_"+action, 1}, // Identity for sanity check
                //{"Distance", (decimal)Math.Abs(end-newVal)}
                { "Distance_Change", Math.Abs(end - newVal) - Math.Abs(end - value) }
            }));
        }
예제 #3
0
        public override Dictionary <QFeature, decimal> GetFeatures(QAction action)
        {
            Point   self       = ((Maze)GetNewState(action)).self;
            QSearch qsearch    = new QSearch(this);
            Maze    simpleMaze = new Maze()
            {
                maze = maze, self = self, goal = goal, width = width, height = height, walls = walls.ToArray()
            };
            QSearchResult bestPath = qsearch.AStar(simpleMaze);

            List <Point> bestOppMoves = new List <Point>();

            foreach (Point o in opponent)
            {
                bestOppMoves.Add(o);
                bestOppMoves.Add(new Point(o.X + 1, o.Y));
                bestOppMoves.Add(new Point(o.X - 1, o.Y));
                bestOppMoves.Add(new Point(o.X, o.Y + 1));
                bestOppMoves.Add(new Point(o.X, o.Y - 1));
            }
            foreach (Point o in bestOppMoves.ToArray())
            {
                bestOppMoves.Add(new Point(o.X + 1, o.Y));
                bestOppMoves.Add(new Point(o.X - 1, o.Y));
                bestOppMoves.Add(new Point(o.X, o.Y + 1));
                bestOppMoves.Add(new Point(o.X, o.Y - 1));
            }
            Maze safeMaze = new Maze()
            {
                maze = maze, self = self, goal = goal, width = width, height = height, walls = walls.Concat(bestOppMoves).ToArray()
            };
            QSearchResult safePath = qsearch.AStar(safeMaze);
            Dictionary <string, decimal> features = new Dictionary <string, decimal>()
            {
                //{this.GetHashCode().ToString()+"_"+action, 1}, // Identity to convert this back to QLearning
                { "Goal", goal == self? 1:0 },
                { "Direct_Distance_To_Goal", bestPath == null? 1:(decimal)bestPath.Count / (decimal)(width * height) },
                { "Safe_Distance_To_Goal", (safePath == null? 1: (decimal)safePath.Count / (decimal)(width * height)) }
            };

            decimal distanceToOpponent = decimal.MaxValue;

            if (opponent.Any())
            {
                features["Opponent"] = goal != self && opponent.Where(p => (Math.Abs(p.X - self.X) <= 1 && p.Y == self.Y) || (Math.Abs(p.Y - self.Y) <= 1 && p.X == self.X)).Any() ? 1 : 0;

                distanceToOpponent = opponent.Select(o => qsearch.AStar(new Maze()
                {
                    maze = maze, self = self, goal = o, width = width, height = height, walls = walls
                })).Select(x => x == null? width * height:x.Count).Min();
                features["Distance_To_Opponent"] = distanceToOpponent >= 5? 1:distanceToOpponent / (decimal)(width * height);

                if (goal != self)
                {
                    Maze deadEnd = new Maze()
                    {
                        maze = maze, self = self, goal = goal, width = width, height = height, walls = walls.Concat(new Point[] { new Point(this.self.X - 1, this.self.Y), new Point(this.self.X + 1, this.self.Y), new Point(this.self.X, this.self.Y - 1), new Point(this.self.X, this.self.Y + 1) }).ToArray()
                    };
                    QSearchResult deadPath = qsearch.Depth_First(deadEnd);
                    if (deadPath == null)
                    {
                        features["Dead_End"] = 1;
                    }
                }
            }



            return(QFeature_String.FromStringDecimalDictionary(features));
        }