public void Intersect(SuggestedMoves moves)
 {
     IEnumerator<SuggestedMove> thisEnumerator = Moves.GetEnumerator();
     IEnumerator<SuggestedMove> otherEnumerator = moves.Moves.GetEnumerator();
     while (thisEnumerator.MoveNext() && otherEnumerator.MoveNext())
     {
         SuggestedMove thisSuggestedMove = thisEnumerator.Current;
         SuggestedMove otherSuggestedMove = otherEnumerator.Current;
         thisSuggestedMove.Intersect(otherSuggestedMove);
     }
     moves.Moves = null; //trash the other data
 }
        public SuggestedMoves GetPath(Color[,] board)
        {
            //Get the farthest nodes
            TreeNode head = MapBuilder.BuildTree(board);
            ISet<TreeNode> farthestNodes = new HashSet<TreeNode>();
            int highestDepth = 0;
            foreach (TreeNode node in head.BFS()) //DFS would be better
            {
                int depth = GetDepth(node);
                if (depth > highestDepth)
                {
                    highestDepth = depth;
                    farthestNodes.Clear();
                    farthestNodes.Add(node);
                }
                else if (depth == highestDepth)
                {
                    farthestNodes.Add(node);
                }
            }

            Console.Write("Farthest nodes are ");
            farthestNodes.Select(n => n.Color).ToList().ForEach(c => Console.Write(c + ", "));
            Console.WriteLine("\r\nFarthest node is " + GetDepth(farthestNodes.First()) + " away from the current");

            //get the color that would step towards each color
            IDictionary<Color, int> tally = new Dictionary<Color, int>();
            foreach (TreeNode farthestNode in farthestNodes)
            {
                TreeNode currentNode = farthestNode;
                while (currentNode.Parent != head)
                {
                    currentNode = currentNode.Parent;
                }
                if (!tally.ContainsKey(currentNode.Color))
                {
                    tally.Add(currentNode.Color, 1);
                }
                else
                {
                    tally[currentNode.Color]++;
                }
            }
            SuggestedMoves suggestedMoves = new SuggestedMoves();
            suggestedMoves.AddFirst(new SuggestedMove(tally.OrderByDescending(kvp => kvp.Value).Select(n => n.Key)));
            return suggestedMoves;
        }
        public override SuggestedMoves ChooseColor(Model.Color[,] board)
        {
            SuggestedMove move = new SuggestedMove();
            foreach(Color color in Enum.GetValues(typeof(Color)))
            {
                if (!recentColors.Contains(color))
                {
                    move.AddSuggestion(color, 100);
                }
            }
            int index = 1;
            foreach (Color color in recentColors)
            {
                move.AddSuggestion(color, index++);
            }

            var moves = new SuggestedMoves();
            moves.AddFirst(move);
            return moves;
        }
        public override SuggestedMoves ChooseColor(Color[,] board)
        {
            MapNode head = MapBuilder.BuildMap(board);
            ISet<MapNode> firstLayer = head.GetNeighbors();
            List<Color> possibleColorsToClear = firstLayer.Select(node => node.Color).ToList();

            IEnumerator<MapNode> breathFirstSearch = head.BFS().GetEnumerator();

            while(breathFirstSearch.MoveNext() && possibleColorsToClear.Count > 0)
            {
                MapNode currentNode = breathFirstSearch.Current;
                if (!firstLayer.Contains(currentNode))
                {
                    //can't wipe out that color, it is behind the first layer
                    possibleColorsToClear.Remove(currentNode.Color);
                }
            }

            SuggestedMove move = new SuggestedMove(possibleColorsToClear);
            SuggestedMoves moves = new SuggestedMoves();
            moves.AddFirst(move);
            return moves;
        }