htzaar-0.0.2: src/AI/Utils.hs
-- | Utilities for AI players.
module AI.Utils
( winNext
, boardHeuristic
, pruneBoardTree
) where
import Data.Function
import Data.List
import Board
-- | Searches BoardTree to a depth of 1 looking for a guaranteed win.
winNext :: Strategy -> Strategy
winNext s (BoardTree a b branches) = s $ BoardTree a b $ if null winning then branches else [head winning]
where
winning = [ (t, b) | (t, b@(BoardTree _ _ [])) <- branches ]
-- | Applies board heuristic to all next board states. Selects the turn at achieves the board with the lowest cost function.
boardHeuristic :: Ord a => (Board -> a) -> Strategy
boardHeuristic cost (BoardTree _ _ branches) g = (optimalTurn, g)
where
turns = [ (t, cost board) | (t, BoardTree _ board _) <- branches ]
(optimalTurn, _) = minimumBy (compare `on` snd) turns
-- | Prunes the board tree with a board predicate. If pruning removes all turns, no pruning is done.
pruneBoardTree :: (Board -> Bool) -> BoardTree -> BoardTree
pruneBoardTree f bt@(BoardTree a b branches) = if null branches' then bt else BoardTree a b branches'
where
branches' = [ (t, bt) | (t, bt@(BoardTree _ b _)) <- branches, f b ]
{-
losing = [ t | (t, (BoardTree _ _ branches)) <- branches, (_, (BoardTree _ _ [])) <- branches ]
branches1 = if not $ null winning
then [head winning]
else if length branches < 100 then [ (t, b) | (t, b) <- branches, notElem t losing ] else branches
branches2 = if null branches1 then [head branches] else branches1
-}