Is it important for move representation to be small ?

Discussion of chess software programming and technical issues.

Moderator: Ras

OneTrickPony
Posts: 160
Joined: Tue Apr 30, 2013 1:29 am

Is it important for move representation to be small ?

Post by OneTrickPony »

(First, let me know if I am asking too many questions here; if so I will limit myself a bit).

So I am reading about how moves are represented and it's often all kind of bit trickery, like here: http://chessprogramming.wikispaces.com/Encoding+Moves describing how to fit move representation into 16bits.

Is it important though ? Can't I just make:
struct move {
int from;
int to;
int type;
};

?
List of moves exists in only one node at the time anyway so it won't be too big. I won't be storing moves anywhere (I think ?) and using this will be convenient. Am I missing something here ?
elcabesa
Posts: 858
Joined: Sun May 23, 2010 1:32 pm

Re: Is it important for move representation to be small ?

Post by elcabesa »

list of moves are stored for every node you are actually doing alphaBeta search.
at depth 10 you'll have 10 movelist at the same time because of recursion but I don' think this is a problem with the GB of memory a modern PC has.

The need of compact move representation came from storing the best move of a position in the transposition table. sometimes you'll need to store the best move and the threat move ( the move the opponent is threating to do , it cam from NULL MOVE test ).

smaller move representation means more element in the transposition table with the same MB
lucasart
Posts: 3243
Joined: Mon May 31, 2010 1:29 pm
Full name: lucasart

Re: Is it important for move representation to be small ?

Post by lucasart »

OneTrickPony wrote:(First, let me know if I am asking too many questions here; if so I will limit myself a bit).

So I am reading about how moves are represented and it's often all kind of bit trickery, like here: http://chessprogramming.wikispaces.com/Encoding+Moves describing how to fit move representation into 16bits.

Is it important though ? Can't I just make:
struct move {
int from;
int to;
int type;
};

?
List of moves exists in only one node at the time anyway so it won't be too big. I won't be storing moves anywhere (I think ?) and using this will be convenient. Am I missing something here ?
Just do what you feel is right, and modify it later as needed. Here's how it happenned in my engine DiscoCheck, chronologically:
(i) first I used a struct with 'int' elements in it: keep it simple unless there's a reason not to.
(ii) then I realized that I needed to keep my TT entries small, so I packed the struct using compiler managed bitfields. An trivial code modification, nice and portable, nice to rely on our good friend the compiler to manage the gory details.
(iii) then I realize that the compiler sucks horribly at managing bitfields, and that you get a significant performance gain by doing it manually (bit shifting, filtering etc.) At least that was my experience with GCC 4.6.
Theory and practice sometimes clash. And when that happens, theory loses. Every single time.
jdart
Posts: 4420
Joined: Fri Mar 10, 2006 5:23 am
Location: http://www.arasanchess.org

Re: Is it important for move representation to be small ?

Post by jdart »

I use a 64-bit move representation for most internal purposes. This allows me to store a bunch of useful information including the piece that is moved, the piece that is captured, and some flags from the move generator, e.g. which phase the move was generated in.

However, the moves in the hashtable are condensed to 3 bytes: start, dest, and promotion (if any). The move is "reconstituted" back into the 64-bit form when it is read out of the hashtable.

--Jon
User avatar
hgm
Posts: 28452
Joined: Fri Mar 10, 2006 10:06 am
Location: Amsterdam
Full name: H G Muller

Re: Is it important for move representation to be small ?

Post by hgm »

As moves are moved around a lot in the move list for sorting, I usually pack them into an integer:

move = key << 24 | from << 8 | to;

where 'key' is the sort key (like MVV/LVA). (In HaChu I shift 'from' by 12 bits in stead of 8, to allow the square numbers to run upto 4096.)

In the hash table I only use the 16 least-significant bits of the move. And often some of the bits that are not used for square numbers can be used for the upper-bound / lower-bound flag, or other flags.

To avoid the need of a separate field for special moves (which would almost never be used), I usually encode these with off-board to-squares.
Karlo Bala
Posts: 373
Joined: Wed Mar 22, 2006 10:17 am
Location: Novi Sad, Serbia
Full name: Karlo Balla

Re: Is it important for move representation to be small ?

Post by Karlo Bala »

OneTrickPony wrote:(First, let me know if I am asking too many questions here; if so I will limit myself a bit).

So I am reading about how moves are represented and it's often all kind of bit trickery, like here: http://chessprogramming.wikispaces.com/Encoding+Moves describing how to fit move representation into 16bits.

Is it important though ? Can't I just make:
struct move {
int from;
int to;
int type;
};

?
List of moves exists in only one node at the time anyway so it won't be too big. I won't be storing moves anywhere (I think ?) and using this will be convenient. Am I missing something here ?
NO. Just use the simplest form. There are 1000 things to do before the speed/size optimisations.
Best Regards,
Karlo Balla Jr.
AlvaroBegue
Posts: 932
Joined: Tue Mar 09, 2010 3:46 pm
Location: New York
Full name: Álvaro Begué (RuyDos)

Re: Is it important for move representation to be small ?

Post by AlvaroBegue »

Other than using a small type for the transposition tables, I also like using the 16-bit move type because I can use the higher 16 bits for sorting: I store a heuristic value there and sort the moves as regular 32-bit unsigned integers.
User avatar
Don
Posts: 5106
Joined: Tue Apr 29, 2008 4:27 pm

Re: Is it important for move representation to be small ?

Post by Don »

OneTrickPony wrote:(First, let me know if I am asking too many questions here; if so I will limit myself a bit).

So I am reading about how moves are represented and it's often all kind of bit trickery, like here: http://chessprogramming.wikispaces.com/Encoding+Moves describing how to fit move representation into 16bits.

Is it important though ? Can't I just make:
struct move {
int from;
int to;
int type;
};

?
List of moves exists in only one node at the time anyway so it won't be too big. I won't be storing moves anywhere (I think ?) and using this will be convenient. Am I missing something here ?
I pack a move into an integer. 6 bits for origin, 6 for destination and there is 3 bits to make it easy to detect special moves. I use a flag for a double pawn move too as a convenience and it all fits in 6 bits.

This all easily fits in 16 bits and for the move generators that sort move I use the upper 16 bits as a sort field. Then the simple insertion sort is a simple sort of a list of ints.

Is that best? I have no idea. The move generation in Komodo is "staged", I generate moves in chunks in an attempt to avoid as much as possible the most expensive phase where I generate and sort the quiet moves.

Don
Capital punishment would be more effective as a preventive measure if it were administered prior to the crime.
OneTrickPony
Posts: 160
Joined: Tue Apr 30, 2013 1:29 am

Re: Is it important for move representation to be small ?

Post by OneTrickPony »

I pack a move into an integer. 6 bits for origin, 6 for destination and there is 3 bits to make it easy to detect special moves. I use a flag for a double pawn move too as a convenience and it all fits in 6 bits.
Do you also keep square to piece table for make_move function to figure out which bit boards to update ?
I am thinking about packing this info to move itself. For now I am sticking to big struct but in the future if I use 32 bits like you and other posters here I could use some of this space to store information about piece type as well.

If I make all my function relying on square to piece table on the other hand it will be difficult to change later. Thoughts ?
User avatar
Don
Posts: 5106
Joined: Tue Apr 29, 2008 4:27 pm

Re: Is it important for move representation to be small ?

Post by Don »

OneTrickPony wrote:
I pack a move into an integer. 6 bits for origin, 6 for destination and there is 3 bits to make it easy to detect special moves. I use a flag for a double pawn move too as a convenience and it all fits in 6 bits.
Do you also keep square to piece table for make_move function to figure out which bit boards to update ?
I am thinking about packing this info to move itself. For now I am sticking to big struct but in the future if I use 32 bits like you and other posters here I could use some of this space to store information about piece type as well.

If I make all my function relying on square to piece table on the other hand it will be difficult to change later. Thoughts ?
I maintain a bit board for every piece/color. pcs[2][7] where type zero is all the pieces of that color. In addition, as suggest to me by Richard Vida I maintain a 64 byte "board" to make it easy to determine what is setting on a specific square.

There are many ways to maintain the bit boards, you can have a "white" bit board and a "black" bit board and then for ALL pieces of a particular type and that would be more compact but at slightly more computational expense for some operations. I don't know which is better or if makes any difference so you might want to experiment.
Capital punishment would be more effective as a preventive measure if it were administered prior to the crime.