I'm making a chess game, and the problem I ran into was how I would organize the "grid" of the board.
I need a way for it to match up the cursor location with a grid square and from there determine whether or not a piece is there, and if one is, which type.
The answer is probably Arrays, but how would I use them to achieve what I want?
Grid help
You should use an 8x8 array:
DIM BOARD[8,8]Access each square with BOARD[Y,X] (yes, Y and X are reversed) You could use numbers to store which piece is on each spot, like 0=empty, 1=white pawn, 2=white rook, etc. (or use a string array and use the names of the pieces) And to fill the array with pieces at the start, you should use COPY:
COPY BOARD,@RESET @RESET DATA 2,3,4,5,6,4,3,2 DATA 1,1,1,1,1,1,1,1 DATA 0,0,0,0,0,0,0,0 DATA ...
thanks, that makes sense.
if anyone else sees this and think they have another good method, don't hesitate to share it. it'll only widen my understanding.
This is what I recommend doing:
These are just things that I have done:
Create the board array as a one-dimensional array from 0 to 63
Define the black and white pieces in alternating order, so
- 0=Empty Space
- 1=Black Pawn
- 2=White Pawn
- 3=Black Knight
- 4=White Knight
- 5=Black Bishop
- 6=White Bishop
- 7=Black Rook
- 8=White Rook
- 9=Black Queen
- 10=White Queen
- 11=Black King
- 12=White King
DIM BOARD[64] RESETBOARD DEF RESETBOARD RESTORE @NEWBOARD FOR I=0 TO 63 READ BOARD[I] NEXT @NEWBOARD DATA 7,3,5,11,9,5,3,7 DATA 1,1,1,1,1,1,1,1 DATA 0,0,0,0,0,0,0,0 DATA 0,0,0,0,0,0,0,0 DATA 0,0,0,0,0,0,0,0 DATA 0,0,0,0,0,0,0,0 DATA 2,2,2,2,2,2,2,2 DATA 8,4,6,12,10,6,4,8 END 'Here are a few extra functions that may help you 'FAST FUNCTION TO CHECK IF AN X,Y POSITION IS WITHIN BOUNDS OF THE BOARD DEF INBOUNDS(X,Y) RETURN X>=0&&Y>=0&&X<8&&Y<8 END 'EXTRACT THE X VALUE OUT OF AN INDEX DEF GETXINDEX(N) IF N>=0&&N<64 THEN RETURN N MOD 8 ELSE RETURN -1 END 'EXTRACT THE Y VALUE OUT OF AN INDEX DEF GETYINDEX(N) IF N>=0&&N<64 THEN RETURN N DIV 8 ELSE RETURN -1 END 'CONVERT FROM X AND Y TO A SINGLE INDEX FROM 0-63 DEF GETINDEX(X,Y) IF !INBOUNDS(X,Y) THEN RETURN -1 RETURN Y*8+X END '-1=ERROR '0=PAWN '1=KNIGHT '2=BISHOP '3=ROOK '4=QUEEN '5=KING DEF GETPIECE(X,Y) IF !INBOUNDS(X,Y) THEN RETURN -1 RETURN (BOARD[Y*8+X]-1) DIV 2 END '-1=ERROR '0=BLACK '1=WHITE DEF GETCOLOR(X,Y) IF !INBOUNDS(X,Y) THEN RETURN -1 RETURN BOARD[Y*8+X] MOD 2 ENDIf you are trying to build a chess AI
- Create a function that can list all the possible positions a piece can be placed with the current board situation
- Create a scoring system to determine which of those moves will give you the most points
- Find a minimax algorithm, preferably alpha-beta-pruning, which will use logic to search a certain depth (like 5 moves ahead) in a tree-like structure to rank each path and find the path that has the highest score.
Why use specifically a 1D array for your approach instead of a 2D [Y,X] one like 12Me did? Here they should be identical aside from how you're indexing them, unless I'm missing something.
Also instead of doing this here:
RESTORE @NEWBOARD FOR I=0 TO 63 READ BOARD[I] NEXTYou can do this:
COPY BOARD, @NEWBOARDEDIT: 12Me already mentioned COPY but oh well.
I chose one dimensional so that positions on the board can be a single number instead of two
It's not a big deal, but I find it easier to manage when dealing with more complex functions
Like making a function GETBESTMOVE, you can simply make it return one number and avoid the OUT X,Y at the end
I just thought it'd be simpler on the user
Also that array initialization... Wow! Efficiency
That's a neat trick
I thought it might be better to number the pieces like 0=empty, 1=white pawn, -1=black pawn, 2=white rook, -2=black rook, etc.
That way you can check the owner of a piece with SGN, and the type of piece with ABS.
DIM BOARD[8,8] COPY BOARD,@RESET ABS(BOARD[Y,X]) 'get piece SGN(BOARD[Y,X]) 'get colorWhen moving a piece, SWAP is probably the best way:
'check color of piece at new position VAR COL=SGN(BOARD[NEWY,NEWX]) 'if the space doesn't have one of your own pieces IF COL!=PLAYER THEN 'if space has one of the other player's pieces, capture it IF COL==-PLAYER THEN BOARD[NEWY,NEWX]=0 'move your piece SWAP BOARD[OLDY,OLDX],BOARD[NEWY,NEWX] ENDIF
I didn't know you could put Data in a function or the copy trick. Very nice. My only addition to the thread would be to make some named pseudo constants so your code is more readable. Something like if piece == KNIGHT_BLACK then is much easier to read when debugging months later than if piece == -24 then. I like the sign idea too, very nice.
I didn't know you could put Data in a function or the copy trick. Very nice. My only addition to the thread would be to make some named pseudo constants so your code is more readable. Something like if piece == KNIGHT_BLACK then is much easier to read when debugging months later than if piece == -24 then. I like the sign idea too, very nice.Yeah, that would be a good idea. Maybe just KNIGHT for white and -KNIGHT for black would be enough. oh, and if you're going to use the default chess pieces, you should number them in the same order, which is pawn, rook, knight, bishop, queen, king
thanks again for all the help. I didn't expect so many people to pitch in.