Geschrieben von: / Posted by: Sune Fischer at 26 April 2002 14:39:50:
Als Antwort auf: / As an answer to: question about opening book and learning geschrieben von: / posted by: Uri Blass at 26 April 2002 13:25:56:
I try to implement book and learning in my program.
The target of the learning is simply to change the choice of the first move
in every game(I may change it later to change the choice of the first move only after a loss or a draw).
The program has a textfile of 2 chars when the first char tells it the first move with white and the second char tells it the first move with black.
The program always learn to change the first move with white from e4 to d4 and in the next game again to e4
The program also always change the first move with black from 1...Nf6 to 1...Nc6 and back to 1...Nf6 with the exception that it does not choose
1...Nc6 against 1.d4 and prefers 1...d6(I could choose 1...d5 but I do not like the fact that after 1.d4 d5 2.c4 my program plays dxc4 and tries to defend the pawn).
Here is the relevant part of my program.
I am interested in ideas how to build better opening book(I know that there are a lot of free programs but I know that there are a lot of files in them and the main reason that I almost did not look at other programs except tscp is the fact that I did not know which file to look first).
If it is just the opening move, it is easier to just put these few moves into a small array and then pick one by random.
My book is not very advanced, no statistics no transpositions of any kind (it can't get back into the book once out).
I use notation such as this:
d2d3e7e5 g2g3d7d5 g1f3b8c6 f1g2g8f6 e1g1f8e7 c2c4d5c4
d2d3e7e6 b1d2d7d5 e2e4g8f6 g1f3c7c5 g2g3b8c6 f1g2f8e7
d2d3g7g6 g2g3f8g7 f1g2d7d5 g1f3e7e5 e1g1g8e7 b1d2e8g8
d2d3g7g6 g2g3f8g7 f1g2d7d5 g1f3g8f6 e1g1c7c5 c2c4e8g8
d2d3g8f6 g1f3d7d5 g2g3c7c5 f1g2b8c6 e1g1e7e6 c2c4f8e7
d2d4b7b5 g1f3c8b7 e2e3a7a6 a2a4b5b4 c2c4g8f6 f1d3g7g6
d2d4b8c6 e2e4e7e5 g1f3e5d4 f3d4d8f6 d4b5f8c5 d1e2c5b6
d2d4b8c6 f2f4d7d5 e2e3g8f6 f1d3c6b4 d3e2c8f5 b1a3e7e6
(the empty space infront is needed)
The code to read it is fairly simple, it builds a streng out of the moves that has been played so far, and then checks if that string matches anyone of the lines in the book. If it finds more than one matching line, it will pick one random of those that were valid. It will then read the next move from the line and check if there is a legal move in that position that matches (there should be or else the book is corrupt, and returns the legal move that matches the move from the book.
Here is the code, you will have to make guesses at what some of the stuff mean, but I think it is not impossible, or else you can ask away.
/*-------------------------------------------------\
| This reads an opening book in the format *.sff, |
| sff is short for "Simple Frenzee Format". |
\-------------------------------------------------*/
MOVE ReadBook(BOARD b)
{
FILE *stream_book;
int linenr[50000];
char linein[2000];
char variation[2000];
int count=0;
int picknumber;
int linecount=0;
unsigned int xb,yb,xe,ye;
int i;
int n;
// init and open book
stream_book=fopen(BookFile,"r");
if (stream_book==NULL)
{
UseBook=false;
sOutput("No book found");
return(BLANKMOVE);
}
memset(linenr,0, 50000*sizeof(int));
memset(linein,'\0', 2000*sizeof(char));
memset(variation,'\0',2000*sizeof(char));
// build variation string:
n=0;
for (i=1;istrlen(variation)+2)
{
count++;
linenr[count]=linecount;
}
memset(linein,'\0',2000*sizeof(char));
}
fprintf(Stream,"active lines in book: %d\n",count);
// check for out of book:
if (count==0)
{
UseBook=false;
fprintf(Stream,"Out of book moves...\n");
fclose(stream_book);
return(BLANKMOVE);
}
// pick a number (variant):
picknumber=(rand()%count)+1;
fprintf(Stream,"picknumber: %d\n",picknumber);
// get the line:
linecount=0;
fseek( stream_book, 0, SEEK_SET );
while (!feof(stream_book)) {
fgets(linein,500,stream_book);
linecount++;
if (linecount==linenr[picknumber])
break;
}
fprintf(Stream,"line %d: %s",linenr[picknumber],linein);
// extract the move from the string:
if (Tree.ply_official%2==0) n=1;
else n=0;
xb = Char2( linein[strlen(variation)+0+n] );
yb = Char2( linein[strlen(variation)+1+n] );
xe = Char2( linein[strlen(variation)+2+n] );
ye = Char2( linein[strlen(variation)+3+n] );
xb = XYcombSQ[xb][yb];
xe = XYcombSQ[xe][ye];
fclose(stream_book);
// return the move:
for (i=0;i