예제 #1
0
        public List <CoinsState> FindMoves(CoinsState state)
        {
            List <CoinsState> states = new List <CoinsState>();

            var one = state.Copy();

            one.Parent = state;
            one.FirstCoin.ChangeSide();
            one.SecondCoin.ChangeSide();
            states.Add(one);

            var two = state.Copy();

            two.Parent = state;
            two.FirstCoin.ChangeSide();
            two.ThirdCoin.ChangeSide();
            states.Add(two);

            var three = state.Copy();

            three.Parent = state;
            three.ThirdCoin.ChangeSide();
            three.SecondCoin.ChangeSide();
            states.Add(three);

            return(states);
        }
예제 #2
0
 public CoinsState(Coin first, Coin second, Coin third, CoinsState parent)
 {
     this.FirstCoin  = first;
     this.SecondCoin = second;
     this.ThirdCoin  = third;
     this.Parent     = parent;
 }
예제 #3
0
        public static void FindPath(CoinsState state)
        {
            Stack <CoinsState> s = new Stack <CoinsState>();

            while (true)
            {
                if (state.Parent != null)
                {
                    s.Push(state);
                    state = state.Parent;
                }
                else
                {
                    if (s.Count > 0)
                    {
                        var count = s.Count;
                        Console.WriteLine($"1. {Coin.Side.Eagle}-{Coin.Side.Tails}-{Coin.Side.Eagle}");
                        for (int i = 0; i < count; i++)
                        {
                            Console.WriteLine($"{i+2}. {s.Peek().FirstCoin.UpperSide}-{s.Peek().SecondCoin.UpperSide}-{s.Peek().ThirdCoin.UpperSide}");
                            s.Pop();
                        }
                        return;
                    }
                }
            }
        }
예제 #4
0
        public CoinsState Copy()
        {
            CoinsState b = new CoinsState(new Coin(this.FirstCoin.UpperSide), new Coin(this.SecondCoin.UpperSide), new Coin(this.ThirdCoin.UpperSide), this);

            return(b);
        }
예제 #5
0
        public static void Bms(int beamSize, CoinsState start = null)
        {
            if (start == null)
            {
                start = new CoinsState();
            }

            Func <CoinsState, int> heuristic = ca =>
            {
                if (ca.FirstCoin.UpperSide == start.FirstCoin.UpperSide && ca.SecondCoin.UpperSide == start.SecondCoin.UpperSide && ca.FirstCoin.UpperSide == start.ThirdCoin.UpperSide)
                {
                    return(1);
                }
                else
                {
                    return(2);
                }
            };

            List <CoinsState> beam    = new List <CoinsState>();
            List <CoinsState> set     = new List <CoinsState>();
            List <CoinsState> visited = new List <CoinsState>();

            visited.Add(start);
            beam.Add(start);

            int step = 0;

            while (beam.Count != 0)
            {
                set.Clear();

                foreach (var c0 in beam)
                {
                    ++step;

                    foreach (var child in c0.FindMoves(c0))
                    {
                        if (visited.Contains(child))
                        {
                            continue;
                        }

                        visited.Add(child);
                        set.Add(child);

                        if (child.IsSolution())
                        {
                            if (step < 3)
                            {
                                visited.Remove(child);
                            }
                            else
                            {
                                Console.WriteLine($"Beam search; beamSize:{beamSize}");
                                FindPath(child);
                                return;
                            }
                        }
                    }
                }

                beam.Clear();
                beam.AddRange(set.OrderBy(heuristic).Take(beamSize));
            }

            Console.WriteLine($"Beam search; Not found; beamSize:{beamSize}");
        }