📄 board.java
字号:
// Copyright (c) 2005 Sony Ericsson Mobile Communications AB
//
// This software is provided "AS IS," without a warranty of any kind.
// ALL EXPRESS OR IMPLIED CONDITIONS, REPRESENTATIONS AND WARRANTIES,
// INCLUDING ANY IMPLIED WARRANTY OF MERCHANTABILITY, FITNESS FOR A
// PARTICULAR PURPOSE OR NON-INFRINGEMENT, ARE HEREBY EXCLUDED.
//
// THIS SOFTWARE IS COMPLEMENTARY OF JAYWAY AB (www.jayway.se)
package bluegammon.logic;
import java.io.DataInputStream;
import java.io.DataOutputStream;
import java.io.IOException;
/**
* <p>
* Representing a game state and basic logic for modifying and querying.
* The methods are based upon a structure
* consisting of board index, white positions, and black positions. The indices
* and the white positions are identical, the black positions are inversed indices.
* </p><p>
* If a white piece is moved two steps from black home, it is moved from index 0 to index 2,
* from white position 0 to white position 2. If a black piece is moved two steps from white
* home, it is moved from index 23 to index 21, from black position 0 to black position 2.
* </p><p>
* From position's point of view, position of pieces are increased. From index' point of view,
* indices for white are increased, and indices for black are decreased as the game continues.
* </p><p>
* <pre><code>
* index wPos bPos index wPos bPos
* 24
* 0 0 23 -B--- -W--- 23 23 0
* 1 1 22 -L-H- -H-H- 22 22 1
* 2 2 21 -A-O- -I-O- 21 21 2
* 3 3 20 -C-M- -T-M- 20 20 3
* 4 4 19 -K-E- -E-E- 19 19 4
* 5 5 18 ----- ----- 18 18 5
* =======25======
* 6 6 17 ----- ----- 17 17 6
* 7 7 16 ----- ----- 16 16 7
* 8 8 15 ----- ----- 15 15 8
* 9 9 14 ----- ----- 14 14 9
* 10 10 13 ----- ----- 13 13 10
* 11 11 12 ----- ----- 12 12 11
* </code></pre>
* </p><p>
* This class is used by <code>BoardState</code> and <code>BoardCanvas</code>
* </p>
*
* @author Peter Andersson
*/
public class Board
{
/** Maximum index that is on the diagonals of a backgammon board */
public static final int POS_BOARD = 23;
/** Index of a piece that is out */
public static final int POS_OUT = 24;
/** Index of a piece that is on guard */
public static final int POS_GUARD = 25;
/** Maximum index plus one */
public static final int MAX_POS = 26;
// Piecepositions
/** Black piece array, number of pieces per index */
protected int[] BLACK = new int[MAX_POS];
/** White piece array, number of pieces per index */
protected int[] WHITE = new int[MAX_POS];
public Board() {}
/**
* Initializes the board to start positions
*/
public void setStartPositions()
{
for (int i = 0; i < MAX_POS; i++)
{
BLACK[i] = 0;
WHITE[i] = 0;
}
WHITE[0] = 2;
WHITE[11] = 5;
WHITE[16] = 3;
WHITE[18] = 5;
BLACK[23] = 2;
BLACK[12] = 5;
BLACK[7] = 3;
BLACK[5] = 5;
//BLACK[POS_OUT] = 13;
//BLACK[1] = 2;
}
/**
* Returns if there are any white pieces on specified index
* @param index the board index
*
* @return true if there are any white pieces on the specified index
*/
public boolean isWhite(int index)
{
return WHITE[index] > 0;
}
/**
* Returns number of pieces on specified index. If there are white pieces,
* number of white pieces are returned. If there are black pieces, number of
* black pieces are returned. Otherwise zero is returned.
*
* @param index The board index
* @return Number of pieces on index.
*/
public int countPieces(int index)
{
if (isWhite(index)) return WHITE[index];
else return BLACK[index];
}
/**
* Returns number of pieces on specified index, for specified color.
*
* @param white If white or black pieces are to be counted
* @param index The index
* @return Number of pieces on specified index of specified color
*/
public int countPieces(boolean white, int index)
{
if (white) return WHITE[index];
else return BLACK[index];
}
/**
* Sets number of pieces in specified index
* @param white Piece color
* @param index The board index
* @param pieces Number of pieces to set
*/
public void setPieces(boolean white, int index, int pieces)
{
if (white) WHITE[index] = (byte)(pieces&0xff);
else BLACK[index] = (byte)(pieces&0xff);
}
/**
* Adds a piece on specified index
* @param white Piece color
* @param index The board index to add a piece to
*/
public void addPiece(boolean white, int index)
{
if (white) WHITE[index]++;
else BLACK[index]++;
}
/**
* Removes a piece from specified index
* @param white Piece color
* @param index The board index to remove a piece from
*/
public void removePiece(boolean white, int index)
{
if (white) WHITE[index]--;
else BLACK[index]--;
}
/**
* Returns board index of player
* @param white Player color
* @param pos The position (0-23) for the piece
* @param step How many steps from specified position
* @return The index
*/
public int getPlayerIndex(boolean white, int pos, int step)
{
if (white)
pos += step;
else
pos -= step;
if (white)
return pos;
else
return POS_BOARD - pos;
}
/**
* Returns board index of opponent
* @param white Opponent color
* @param pos The position (0-23) for the piece
* @param step How many steps from specified position
* @return The index
*/
public int getOpponentIndex(boolean white, int pos, int step)
{
if (white)
pos -= step;
else
pos += step;
if (!white)
return pos;
else
return POS_BOARD - pos;
}
/**
* Returns number of pieces still on board.
*
* @param white True for checking white pieces, false for black
* @return Number of pieces on board, not being out.
*/
public int calculatePiecesLeft(boolean white)
{
int[] player = WHITE;
if (!white) player = BLACK;
int piecesLeft = 0;
for (int i = 0; i <= POS_BOARD; i++)
{
piecesLeft += player[i];
}
piecesLeft += player[POS_GUARD];
return piecesLeft;
}
/**
* Return point per piece in current state.
* <ul>
* <li>1 point if loser has at least one piece out.</li>
* <li>2 points if loser does not have any pieces out.</li>
* <li>3 points if loser still has pieces in enemy country.</li>
* </ul>
* @param loserWhite true for white loser, false for black
* @return Number of points
*/
public int calculatePoints(boolean loserWhite)
{
int pts = 1;
int[] loser = WHITE;
if (!loserWhite) loser = BLACK;
if (loser[POS_OUT] == 0)
{
boolean onEnemyGround = loser[POS_GUARD] > 0;
for (int i = 0; !onEnemyGround && i <= 11; i++)
{
onEnemyGround = loser[getPlayerIndex(loserWhite, i, 0)] > 0;
}
if (onEnemyGround)
{
pts = 3;
}
else
{
pts = 2;
}
}
return pts;
}
/**
* Saves the board status to specified data output stream. Format:
* int[] BLACK[MAX_POS];
* int[] WHITE[MAX_POS];
* @param dos Output stream to save to
* @throws IOException
* @return size of data in bytes
*/
public int saveBoard(DataOutputStream dos) throws IOException
{
int len = 0;
for (int i = 0; i < MAX_POS; i++)
{
dos.writeInt(BLACK[i]);
len += 4;
}
for (int i = 0; i < MAX_POS; i++)
{
dos.writeInt(WHITE[i]);
len += 4;
}
return len;
}
/**
* Reads the board status from specified data output stream.
* See <code>saveBoard</code> for format.
* @param dis Input stream to read from
* @throws IOException
* @return size of data in bytes
*/
public int loadBoard(DataInputStream dis) throws IOException
{
int len = 0;
for (int i = 0; i < MAX_POS; i++)
{
BLACK[i] = dis.readInt();
len += 4;
}
for (int i = 0; i < MAX_POS; i++)
{
WHITE[i] = dis.readInt();
len += 4;
}
return len;
}
}
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -