public static TimedMove CreateUndoMove(int wait_before, int wait_after)
        {
            TimedMove timed_move = new TimedMove(new Move(0, 1), wait_before, wait_after);
            timed_move.undo = true;

            return timed_move;
        }
 public GameStateMoveAction(GameState gs, GameState original, long time, TimedMove move, List<TimedMove> madeMoves)
     : base(gs, time)
 {
     this.original = original;
     this.move = move;
     this.madeMoves = madeMoves;
 }
 public TimedMove(TimedMove move)
     : base(move)
 {
     this.wait_before = move.wait_before;
     this.wait_after = move.wait_after;
     this.undo = move.undo;
 }
 public GameStateMoveAction(GameState gs, GameState original, long time, TimedMove move, List <TimedMove> madeMoves)
     : base(gs, time)
 {
     this.original  = original;
     this.move      = move;
     this.madeMoves = madeMoves;
 }
        public static GameStateAction Deserialize(string s)
        {
            string[] t = s.Split('|');

            GameState original = GameState.Deserialize(t[0]);
            GameState gs       = GameState.Deserialize(t[1]);
            long      time     = long.Parse(t[2]);

            /*Stack<Move> madeMoves = new Stack<Move>();
             * foreach (string d in t[2].Split(new string[] { " " }, StringSplitOptions.RemoveEmptyEntries).Reverse())
             * {
             *      Move m = new Move(d);
             *      madeMoves.Push(m);
             * }*/
            List <TimedMove> madeMoves = new List <TimedMove>();

            foreach (string d in t[3].Split(new string[] { " " }, StringSplitOptions.RemoveEmptyEntries))
            {
                TimedMove m = TimedMove.Deserialize(d);
                madeMoves.Add(m);
            }

            TimedMove move = null;

            if (t[4] != "X")
            {
                move = TimedMove.Deserialize(t[4]);
            }

            return(new GameStateMoveAction(gs, original, time, move, madeMoves));
        }
Exemple #6
0
 public TimedMove(TimedMove move)
     : base(move)
 {
     this.wait_before = move.wait_before;
     this.wait_after  = move.wait_after;
     this.undo        = move.undo;
 }
Exemple #7
0
        public static TimedMove CreateUndoMove(int wait_before, int wait_after)
        {
            TimedMove timed_move = new TimedMove(new Move(0, 1), wait_before, wait_after);

            timed_move.undo = true;

            return(timed_move);
        }
Exemple #8
0
        public override TimedPlay TimedPlayOnRoll(GameState gamestate, List <PlayHint> hints, VenueUndoMethod undo_method)
        {
            List <Play> legal_plays  = gamestate.Board.LegalPlays(gamestate.PlayerOnRoll, gamestate.Dice);
            List <Move> forced_moves = Board.ForcedMoves(legal_plays);

            // Sort the moves.
            foreach (PlayHint hint in hints)
            {
                SortMoves(gamestate, hint.Play, legal_plays, forced_moves);
            }

            double optimal_move_equity = hints[0].Equity;

            double doubtful = 0.04;
            double bad      = 0.08;
            double very_bad = 0.16;

            /*List<PlayHint> good_hints = new List<PlayHint>();
             * List<PlayHint> doubtful_hints = new List<PlayHint>();
             * List<PlayHint> bad_hints = new List<PlayHint>();
             * List<PlayHint> very_bad_hints = new List<PlayHint>();
             *
             * // Skip the first one as it is the optimal one.
             * for (int i = 1; i < hints.Count; i++)
             * {
             *  double diff = optimal_move_equity - hints[i].Equity;
             *  if (diff >= very_bad)
             *      very_bad_hints.Add(hints[i]);
             *  else if (diff >= bad)
             *      very_bad_hints.Add(hints[i]);
             *  else if (diff >= doubtful)
             *      doubtful_hints.Add(hints[i]);
             *  else
             *      good_hints.Add(hints[i]);
             * }*/

            /*if (legal_plays.Count != hints.Count)
             * {
             *  Console.WriteLine("Legal plays and hint plays mis-match");
             *  Console.WriteLine("Legal plays: ");
             *  foreach (Play play in legal_plays)
             *      Console.WriteLine(play);
             *  Console.WriteLine("Hint plays: ");
             *  foreach (PlayHint hint in hints)
             *      Console.WriteLine(hint);
             *
             *  throw new Exception();
             * }*/

            // Is the play an obvious move? Check the equity difference to second best move.
            bool obvious_move = false;

            if (legal_plays.Count == 1 || (hints.Count > 1 && (hints[1].Equity - optimal_move_equity) > bad))
            {
                obvious_move = true;
            }

            List <Play> fake_plays = new List <Play>();

            if (!obvious_move && undo_method != VenueUndoMethod.None)
            {
                // Choose the amount of fake plays.
                int fake_plays_to_choose = 0;
                if (random.NextDouble() <= undo_probability)
                {
                    fake_plays_to_choose++;
                    while (random.NextDouble() < 0.1)
                    {
                        fake_plays_to_choose++;
                    }
                }

                // Choose the fake plays.
                for (int i = 0; i < fake_plays_to_choose; i++)
                {
                    int fake_play_index = 1;
                    while (random.Next(3) == 0)
                    {
                        fake_play_index++;
                        if (fake_play_index >= hints.Count)
                        {
                            fake_play_index = 0;
                        }
                    }

                    // Make it partial?
                    if (random.NextDouble() <= 0.3)
                    {
                        Play partial_play    = new Play();
                        int  moves_to_choose = 1;
                        while (random.Next(4) == 0)
                        {
                            moves_to_choose++;
                            if (moves_to_choose >= hints[fake_play_index].Play.Count)
                            {
                                moves_to_choose = 1;
                            }
                        }

                        for (int m = 0; m < moves_to_choose; m++)
                        {
                            partial_play.Add(hints[fake_play_index].Play[m]);
                        }

                        fake_plays.Add(partial_play);
                    }
                    else
                    {
                        fake_plays.Add(hints[fake_play_index].Play);
                    }
                }
            }

            TimedPlay timed_play = new TimedPlay();

            // Add undo sequences using fake plays.
            if (!obvious_move && hints.Count > 1 && fake_plays.Count > 0)
            {
                List <Move> made_moves = new List <Move>();
                //Queue<Move> made_moves = new Queue<Move>();
                //Stack<Move> made_moves = new Stack<Move>();

                foreach (Play fake_play in fake_plays)
                {
                    for (int i = 0; i < fake_play.Count; i++)
                    {
                        /*if (made_moves.Count > 0)
                         * {
                         *  int shared = 0;
                         *  while (shared < made_moves.Count && shared < fake_play.Count && made_moves[shared] == fake_play[shared])
                         *      shared++;
                         * }
                         * else*/
                        timed_play.Add(new TimedMove(fake_play[i], 0, 0));
                        //made_moves.Push(fake_play[i]);
                    }

                    // Undo all
                    if (undo_method == VenueUndoMethod.UndoLast)
                    {
                        for (int i = 0; i < fake_play.Count; i++)
                        {
                            timed_play.Add(TimedMove.CreateUndoMove(0, 0));
                        }
                    }
                    else
                    {
                        timed_play.Add(TimedMove.CreateUndoMove(0, 0));
                    }
                }

                int m = 0;
                // TODO: Some how check if current move and previous share some similar so not necessary undo all.

                foreach (Move move in hints[0].Play)
                {
                    timed_play.Add(new TimedMove(move, 0, 0));
                }
            }
            else
            {
                // No fake plays, add the optimal move.
                foreach (Move move in hints[0].Play)
                {
                    timed_play.Add(new TimedMove(move, 0, 0));
                }
            }


            int  last_from     = -2;
            bool was_last_undo = false;

            foreach (TimedMove timed_move in timed_play)
            {
                if (timed_move.IsUndo)
                {
                    if (was_last_undo)
                    {
                        timed_move.WaitBefore = Gaussian.Next(500, 200, 10000, 600, 1.5);
                        timed_move.WaitAfter  = random.Next(200);
                    }
                    else
                    {
                        timed_move.WaitBefore = Gaussian.Next(1000, 500, 10000, 2000, 1.5);
                        timed_move.WaitAfter  = Gaussian.Next(1000, 50, 10000, 2000, 1.5);
                    }

                    last_from = -2;

                    was_last_undo = true;

                    continue;
                }

                was_last_undo = false;

                if (timed_move.From != last_from)
                {
                    //timed_move.WaitBefore = Gaussian.Next(500, 250, 2000, 500, 3.0);
                    //timed_move.WaitAfter = random.Next(300);
                    timed_move.WaitBefore = Gaussian.Next(1000, 250, 2000, 1000, 3.0);
                    timed_move.WaitAfter  = random.Next(300);
                }
                else
                {
                    //timed_move.WaitBefore = Gaussian.Next(250, 100, 2000, 200, 3.0);
                    //timed_move.WaitAfter = random.Next(100);
                    timed_move.WaitBefore = Gaussian.Next(500, 250, 2000, 200, 3.0);
                    timed_move.WaitAfter  = random.Next(250);
                }

                // Speedup for pure race or when we have a blockade.
                if (random.NextDouble() <= 0.9 && (gamestate.Board.IsPureRace() || HasBlockaded(gamestate) || obvious_move))
                {
                    timed_move.WaitBefore = (int)(timed_move.WaitBefore * (0.4 + 0.3 * random.NextDouble()));
                    timed_move.WaitAfter  = (int)(timed_move.WaitAfter * (0.4 + 0.3 * random.NextDouble()));
                }

                last_from = timed_move.From;
            }

            // Normalize with coefficient.
            foreach (TimedMove timed_move in timed_play)
            {
                timed_move.WaitBefore = (int)(timed_move.WaitBefore * coefficient);
                timed_move.WaitAfter  = (int)(timed_move.WaitAfter * coefficient);
            }

            return(timed_play);
        }
Exemple #9
0
        void Form1_MouseClick(object sender, MouseEventArgs e)
        {
            if (currentGameState.PlayerOnTurn == 0 && !currentGameState.HasOffer && currentGameState.DiceRolled && legalPlays.Count > 0 && madeMoves.Count < legalPlays[0].Count)
            {
                BoundingChequer chequer = ClickTest(e.Location);
                if (chequer == null)
                    return;

                int[] dice = currentGameState.Dice;

                int from = chequer.Slot;

                if (dice[0] != dice[1])
                {
                    int die = -1;
                    if (unusedDice.Count == 2)
                    {
                        if (e.Button == MouseButtons.Left)
                            die = Math.Max(unusedDice[0], unusedDice[1]);
                        else if (e.Button == MouseButtons.Right)
                            die = Math.Min(unusedDice[0], unusedDice[1]);
                        else
                            return;
                    }
                    else
                        die = unusedDice[0];

                    int to = chequer.Slot - die;
                    if (to < -1)
                        to = -1;

                    Move move = new Move(from, to);

                    if (currentGameState.Board.IsLegalMove(currentGameState.PlayerOnRoll, move, die))
                    {
                        if (to >= 0 && currentGameState.Board.PointCount(currentGameState.PlayerOnRoll, to) == -1)
                            move.AddHitPoint(to);

                        watch.Stop();

                        /*Stack<Move> s = new Stack<Move>();
                        foreach (Move m in madeMoves.Reverse())
                            s.Push(m.Clone());*/

                        List<TimedMove> h = new List<TimedMove>();
                        foreach (TimedMove m in moveHistory)
                            h.Add(new TimedMove(m));

                        TimedMove tmove = new TimedMove(move, (int)watch.ElapsedMilliseconds, 0);

                        moves.Add(new GameStateMoveAction(currentGameState.Clone(), originalGameState, watch.ElapsedMilliseconds, tmove, h));

                        currentGameState.Board.MakeMove(currentGameState.PlayerOnRoll, move);
                        madeMoves.Push(move);
                        moveHistory.Add(tmove);

                        unusedDice.Remove(die);
                        usedDice.Push(die);

                        UpdateControls();
                    }
                    else
                    {
                        if (unusedDice.Count == 2)
                        {
                            die = (dice[0] == die) ? dice[1] : dice[0];

                            to = chequer.Slot - die;
                            if (to < -1)
                                to = -1;

                            move = new Move(from, to);

                            if (currentGameState.Board.IsLegalMove(currentGameState.PlayerOnRoll, move, die))
                            {
                                if (to >= 0 && currentGameState.Board.PointCount(currentGameState.PlayerOnRoll, to) == -1)
                                    move.AddHitPoint(to);

                                watch.Stop();
                                /*Stack<Move> s = new Stack<Move>();
                                foreach (Move m in madeMoves.Reverse())
                                    s.Push(m.Clone());*/

                                //moves.Add(new GameStateMoveAction(currentGameState.Clone(), watch.ElapsedMilliseconds, move.Clone(), s));

                                List<TimedMove> h = new List<TimedMove>();
                                foreach (TimedMove m in moveHistory)
                                    h.Add(new TimedMove(m));

                                TimedMove tmove = new TimedMove(move, (int)watch.ElapsedMilliseconds, 0);

                                moves.Add(new GameStateMoveAction(currentGameState.Clone(), originalGameState, watch.ElapsedMilliseconds, tmove, h));

                                currentGameState.Board.MakeMove(currentGameState.PlayerOnRoll, move);
                                madeMoves.Push(move);
                                moveHistory.Add(tmove);

                                unusedDice.Remove(die);
                                usedDice.Push(die);

                                UpdateControls();
                            }
                        }
                        //else
                        //Console.WriteLine("Illegal move " + from + "/" + to);
                    }
                }
                else
                {
                    int to = chequer.Slot - dice[0];
                    if (to < -1)
                        to = -1;
                    Move move = new Move(from, to);

                    if (currentGameState.Board.IsLegalMove(currentGameState.PlayerOnRoll, move, dice[0]))
                    {
                        if (to >= 0 && currentGameState.Board.PointCount(currentGameState.PlayerOnRoll, to) == -1)
                            move.AddHitPoint(to);

                        watch.Stop();

                        /*Stack<Move> s = new Stack<Move>();
                        foreach (Move m in madeMoves.Reverse())
                            s.Push(m.Clone());

                        moves.Add(new GameStateMoveAction(currentGameState.Clone(), watch.ElapsedMilliseconds, move.Clone(), s));*/

                        List<TimedMove> h = new List<TimedMove>();
                        foreach (TimedMove m in moveHistory)
                            h.Add(new TimedMove(m));

                        TimedMove tmove = new TimedMove(move, (int)watch.ElapsedMilliseconds, 0);

                        moves.Add(new GameStateMoveAction(currentGameState.Clone(), originalGameState, watch.ElapsedMilliseconds, tmove, h));

                        currentGameState.Board.MakeMove(currentGameState.PlayerOnRoll, move);
                        madeMoves.Push(move);
                        moveHistory.Add(tmove);

                        unusedDice.Remove(dice[0]);
                        usedDice.Push(dice[0]);

                        UpdateControls();
                    }
                }
                // Fix problem when making an illegal move the watch resets itsefl
            }
        }
Exemple #10
0
 public void Add(TimedMove timed_move)
 {
     timed_moves.Add(timed_move);
 }
        public static GameStateAction Deserialize(string s)
        {
            string[] t = s.Split('|');

            GameState original = GameState.Deserialize(t[0]);
            GameState gs = GameState.Deserialize(t[1]);
            long time = long.Parse(t[2]);

            /*Stack<Move> madeMoves = new Stack<Move>();
            foreach (string d in t[2].Split(new string[] { " " }, StringSplitOptions.RemoveEmptyEntries).Reverse())
            {
                Move m = new Move(d);
                madeMoves.Push(m);
            }*/
            List<TimedMove> madeMoves = new List<TimedMove>();
            foreach (string d in t[3].Split(new string[] { " " }, StringSplitOptions.RemoveEmptyEntries))
            {
                TimedMove m = TimedMove.Deserialize(d);
                madeMoves.Add(m);
            }

            TimedMove move = null;
            if (t[4] != "X")
                move = TimedMove.Deserialize(t[4]);

            return new GameStateMoveAction(gs, original, time, move, madeMoves);
        }
Exemple #12
0
 public void Add(TimedMove timed_move)
 {
     timed_moves.Add(timed_move);
 }