X-Git-Url: https://git.ucc.asn.au/?p=progcomp2012.git;a=blobdiff_plain;f=samples%2Fforfax%2Fforfax.h;h=4bd747816cb069f89bc0ce4f17b333fb5b33247d;hp=fe370a9942a4ebff77f2c6b8d09d9b8e04f57ec7;hb=041c37d1dfc4a94024fe1d329d289e4c59667885;hpb=f91a915d6f64f9d35e867d26e8ddb9c1b1ab0c1e diff --git a/samples/forfax/forfax.h b/samples/forfax/forfax.h index fe370a9..4bd7478 100644 --- a/samples/forfax/forfax.h +++ b/samples/forfax/forfax.h @@ -1,13 +1,24 @@ +/** + * "forfax", a sample Stratego AI for the UCC Programming Competition 2012 + * Declarations for classes Piece, Board and Forfax, Declaration/Implementation of helper class MovementChoice + * @author Sam Moore (matches) [SZM] + * @website http://matches.ucc.asn.au/stratego + * @email progcomp@ucc.asn.au or matches@ucc.asn.au + * @git git.ucc.asn.au/progcomp2012.git + */ + #ifndef FORFAX_H #define FORFAX_H #include //Uses C++ std::vectors to store pieces #include //Uses C++ std::string -/** - * Header for the sample Stratego AI "forfax" - * @author Sam Moore 2011 - */ -class Board; +#include //For debug +#include //For debug + + + +class Board; //Forward declaration used by class Piece + /** * Class to represent a piece on the board */ @@ -18,7 +29,7 @@ class Piece typedef enum {RED=0, BLUE=1, NONE, BOTH} Colour; //Used for the allegiance of the pieces - terrain counts as NONE. Piece(int newX, int newY,const Colour & newColour); - Piece(int newX, int newY,const Colour & newColour, const Colour & rankKnownBy, const Type & fixedRank); + Piece(int newX, int newY,const Colour & newColour, const Type & fixedRank); virtual ~Piece() {} void SetCoords(int newX, int newY) {x = newX; y = newY;} @@ -30,12 +41,18 @@ class Piece static Type GetType(char fromToken); //Retrieves the type of a piece given its character token static Colour Opposite(const Colour & colour) {return colour == RED ? BLUE : RED;} - + bool Mobile() const + { + if (minRank == maxRank) + return (minRank != Piece::FLAG && minRank != Piece::BOMB); + else + return true; + } int x; int y; const Colour colour; //The colour of the piece - Type minRank[2]; //The minimum possible rank of the piece, according to each colour - Type maxRank[2]; //The maximum possible rank of the piece, according to each colour + Type minRank; //The minimum possible rank of the piece + Type maxRank; //The maximum possible rank of the piece int lastMove; @@ -57,6 +74,8 @@ class Board Piece * Get(int x, int y) const; //Retrieve single piece Piece * Set(int x, int y, Piece * newPiece); //Add piece to board + bool ValidPosition(int x, int y) const {return (x > 0 && x < width && y > 0 && y < height);} + int Width() const {return width;} int Height() const {return height;} @@ -89,39 +108,52 @@ class Board }; /** - * Small class to manage the Forfax AI + * Class to manage the Forfax AI */ class Forfax { public: Forfax(); virtual ~Forfax(); - bool Setup(); //Waits for input to determine colour and board size, and then responds with setup - bool MakeMove(); //Should be called each turn - determines Forfax's move - double CombatSuccessChance(Piece * attacker, Piece * defender, const Piece::Colour & accordingTo) const; - double MovementBaseScore(Piece * move, const Board::Direction & dir, const Piece::Colour & accordingTo) const; - double MovementTotalScore(Piece * move, const Board::Direction & dir, const Piece::Colour & accordingTo) const; + typedef enum {OK, NO_NEWLINE, EXPECTED_ATTACKER, UNEXPECTED_DEFENDER, NO_ATTACKER, NO_DEFENDER, COLOUR_MISMATCH, INVALID_QUERY, BOARD_ERROR, VICTORY} Status; + + Status Setup(); //Waits for input to determine colour and board size, and then responds with setup + Status MakeMove(); //Should be called each turn - determines Forfax's move + + + //Move score functions + double MovementScore(Piece * move, const Board::Direction & dir) const; //Calculate total score + double CombatSuccessChance(Piece * attacker, Piece * defender) const; //Calculate chance of success in combat + double IntrinsicWorth(int x, int y) const; //How much a given point on the board is worth + double VictoryScore(Piece * attacker, Piece * defender) const; //How much killing the defender is worth + double DefeatScore(Piece * attacker, Piece * defender) const; //How much losing is worth + + + void PrintBoard(std::ostream & out); protected: - bool MakeFirstMove(); //Should only be called on the first turn - bool InterpretMove(); + Status MakeFirstMove(); //Should only be called on the first turn + Status InterpretMove(); private: Board * board; //Forfax stores the state on a board Piece::Colour colour; //Forfax needs to know his colour std::string strColour; //String of colour int turnNumber; //Forfax needs to know what turn number it is - int remainingUnits[14][2][2]; //Known remaining units, accessed by (type, colour, accordingTo) + static int remainingUnits[2][15]; //Known remaining units, accessed by [colour][type] }; +/** + * Helper class used to store various moves in the board, and their associated scores + */ class MovementChoice { public: - MovementChoice(Piece * newPiece, const Board::Direction & newDir, const Forfax & forfax, const Piece::Colour & accordingTo) : piece(newPiece), dir(newDir) + MovementChoice(Piece * newPiece, const Board::Direction & newDir, const Forfax & forfax) : piece(newPiece), dir(newDir) { - score = forfax.MovementBaseScore(piece, dir, accordingTo); + score = forfax.MovementScore(piece, dir); } MovementChoice(const MovementChoice & cpy) : piece(cpy.piece), dir(cpy.dir), score(cpy.score) @@ -143,14 +175,6 @@ class MovementChoice }; -class MovementTotalChoice : public MovementChoice -{ - public: - MovementTotalChoice(Piece * newPiece, const Board::Direction & newDir, const Forfax & forfax, const Piece::Colour & accordingTo) : MovementChoice(newPiece, newDir, forfax, accordingTo) - { - score = score/(forfax.MovementTotalScore(piece, dir, Piece::Opposite(accordingTo))); - } -}; #endif //FORFAX_H