Closed Disservin closed 2 years ago
I've actually never done this exercise, I have heard about it and had lingering anxiety that I should try it and check that my code copes well. Thanks for pushing me over the edge; Although my code is battle hardened and I was confident in it, I was still very relieved to find that everything matches the standard numbers reported in https://www.chessprogramming.org/Perft_Results !
I'm not sure what you are doing with the mv.NaturalOut() and the comparison. Here is a complete but minimally altered version of your code that works well;
static thc::ChessRules cr;
int perf(int depth) {
int nodes = 0;
if (depth == 0) {
return 1;
}
else {
std::vector
int main( int argc, char *argv[] ) { for( int i=1; i<=7; i++ ) { cr.Forsyth("rnbqkbnr/pppppppp/8/8/8/8/PPPPPPPP/RNBQKBNR w KQkq - 0 1"); int n = perf(i); printf( "perf(cr,%d) = %d\n", i, n ); } return 0; }
Here is a version that's closer to the reference in the wiki page you link to (importantly it uses 64 bit integers, for example). This version is a bit more optimised too, especially the "PerftFast" version which uses the pseudo legal move refinement suggested in the Wiki (possible because my move generator does work in the way discussed - by generating all moves including moves that illegally leave the king exposed to capture). I did have to make a tiny tweak to thc.h to make the fast version possible, I had to make function GenMoveList() public rather than protected.
typedef unsigned long long u64; u64 Perft( thc::ChessRules &cr, int depth ); u64 PerftFast( thc::ChessRules &cr, int depth );
int main( int argc, char *argv[] ) { for( int i=1; i<=max; i++ ) { thc::ChessRules cr; u64 n = PerftFast(cr,i); printf( "PerftFast(cr,%d) = %lld\n", i, n ); } return 0; }
u64 Perft( thc::ChessRules &cr, int depth ) { thc::MOVELIST movelist; int n_moves, i; u64 nodes = 0;
if( depth == 0 )
return 1ULL;
cr.GenLegalMoveList( &movelist );
n_moves = movelist.count;
for( i=0; i<n_moves; i++)
{
cr.PushMove( movelist.moves[i] );
nodes += Perft( cr, depth-1 );
cr.PopMove( movelist.moves[i] );
}
return nodes;
}
u64 PerftFast( thc::ChessRules &cr, int depth ) { thc::MOVELIST movelist; int n_moves, i; u64 nodes = 0;
if( depth == 0 )
return 1ULL;
cr.GenMoveList( &movelist );
n_moves = movelist.count;
for( i=0; i<n_moves; i++)
{
cr.PushMove( movelist.moves[i] );
bool okay = cr.Evaluate();
if( okay )
nodes += PerftFast( cr, depth-1 );
cr.PopMove( movelist.moves[i] );
}
return nodes;
}
I got these results, matching https://www.chessprogramming.org/Perft_Results ;
PerftFast(cr,1) = 20 PerftFast(cr,2) = 400 PerftFast(cr,3) = 8902 PerftFast(cr,4) = 197281 PerftFast(cr,5) = 4865609 PerftFast(cr,6) = 119060324 PerftFast(cr,7) = 3195901860
On my old slow laptop PerftFast(cr,7) took 6 minutes. Level 8 takes at least an hour, I'll leave it running overnight. I also tried the "Kiwipete" position and pleasingly got;
Perft(cr,1) = 48 Perft(cr,2) = 2039 Perft(cr,3) = 97862 Perft(cr,4) = 4085603 Perft(cr,5) = 193690690
As expected.
On Mon, 24 Jan 2022 at 09:00, disservin @.***> wrote:
Shouldnt that return 400 for depth 2 ? Always returns 4200 for me. Sorry if thats the wrong place to ask here. Read more about Perft on Chessprogramming Wiki https://www.chessprogramming.org/Perft `
int perf(int depth) { int nodes = 0; if (depth == 0) { return 1; } else { cr.GenLegalMoveList(moves, check, mate, stalemate); unsigned int len = moves.size(); for (unsigned int i = 0; i < len; i++) { thc::Move mv = moves[i]; std::string mv_txt = mv.NaturalOut(&cr); if (mv_txt != "--") { cr.PlayMove(mv); nodes += perf(depth - 1); cr.PopMove(mv); } } return nodes; } }
`
— Reply to this email directly, view it on GitHub https://github.com/billforsternz/thc-chess-library/issues/13, or unsubscribe https://github.com/notifications/unsubscribe-auth/ABSQYSV473AVZYXUD2E7OXDUXRM5BANCNFSM5MTX4BAA . Triage notifications on the go with GitHub Mobile for iOS https://apps.apple.com/app/apple-store/id1477376905?ct=notification-email&mt=8&pt=524675 or Android https://play.google.com/store/apps/details?id=com.github.android&referrer=utm_campaign%3Dnotification-email%26utm_medium%3Demail%26utm_source%3Dgithub.
You are receiving this because you are subscribed to this thread.Message ID: @.***>
-- Bill Forster 15A Boundary Road Kelburn Wellington 6012 New Zealand +64 21 357 371 @.***
Hey thanks for the quick replay, your altered version works just fine, the comparison was done because I wanted to see the current move, mv
std::cout << mv_text << std::enl;
However sometimes I didnt get a move back but got "--". Which I thought is some kind of bug ? So I simply tried to skip that part. Great that perft confirmed the move generation. !
Thanks. I did check one more level;
PerftFast(cr,1) = 20 Date/time is: Mon Jan 24 23:25:26 2022 PerftFast(cr,2) = 400 Date/time is: Mon Jan 24 23:25:26 2022 PerftFast(cr,3) = 8902 Date/time is: Mon Jan 24 23:25:26 2022 PerftFast(cr,4) = 197281 Date/time is: Mon Jan 24 23:25:26 2022 PerftFast(cr,5) = 4865609 Date/time is: Mon Jan 24 23:25:26 2022 PerftFast(cr,6) = 119060324 Date/time is: Mon Jan 24 23:25:39 2022 PerftFast(cr,7) = 3195901860 Date/time is: Mon Jan 24 23:31:24 2022 PerftFast(cr,8) = 84998978956 Date/time is: Tue Jan 25 02:07:39 2022
Also;
Perft(cr,1) = 20 Date/time is: Tue Jan 25 02:07:39 2022 Perft(cr,2) = 400 Date/time is: Tue Jan 25 02:07:39 2022 Perft(cr,3) = 8902 Date/time is: Tue Jan 25 02:07:39 2022 Perft(cr,4) = 197281 Date/time is: Tue Jan 25 02:07:39 2022 Perft(cr,5) = 4865609 Date/time is: Tue Jan 25 02:07:40 2022 Perft(cr,6) = 119060324 Date/time is: Tue Jan 25 02:07:55 2022 Perft(cr,7) = 3195901860 Date/time is: Tue Jan 25 02:15:10 2022 Perft(cr,8) = 84998978956 Date/time is: Tue Jan 25 05:22:34 2022
Finally the "Kiwipete" position to one more level too;
PerftFast(cr,1) = 48 Date/time is: Tue Jan 25 07:47:57 2022 PerftFast(cr,2) = 2039 Date/time is: Tue Jan 25 07:47:57 2022 PerftFast(cr,3) = 97862 Date/time is: Tue Jan 25 07:47:57 2022 PerftFast(cr,4) = 4085603 Date/time is: Tue Jan 25 07:47:58 2022 PerftFast(cr,5) = 193690690 Date/time is: Tue Jan 25 07:48:17 2022 PerftFast(cr,6) = 8031647685 Date/time is: Tue Jan 25 08:02:14 2022
Conclusion: All node counts match reference values from https://www.chessprogramming.org/Perft_Results. On my 12 year old creaky Acer laptop Level 8 for the opening position takes 3 hours 7 minutes (default), or 2 hours 36 (pseudo move optimisation) - not as big a speedup as I would have guessed actually. Each level takes 20-30 times longer than the previous level (makes sense, about the average number of moves in a position), so I could probably go Kiwipete level 7 in about 8 hours. Not sure whether I'll bother as there's no reference value to compare against. But I am motivated to resolve the 2645 or 2637? question about double checks in the Kiwipete position! I might do it on the weekend, it just needs an int AttackedSquareCount() type function to supplement the existing bool AttackedSquare().
On Mon, 24 Jan 2022 at 22:32, disservin @.***> wrote:
Hey thanks for the quick replay, your altered version works just fine, the comparison was done because I wanted to see the current move, mv std::cout << mv_text << std::enl; However sometimes I didnt get a move back but got "--". Which I thought is some kind of bug ? So I simply tried to skip that part. Great that perft confirmed the move generation. !
— Reply to this email directly, view it on GitHub https://github.com/billforsternz/thc-chess-library/issues/13#issuecomment-1019894503, or unsubscribe https://github.com/notifications/unsubscribe-auth/ABSQYSVV5DJ53QYGXXKB5OLUXUMBJANCNFSM5MTX4BAA . Triage notifications on the go with GitHub Mobile for iOS https://apps.apple.com/app/apple-store/id1477376905?ct=notification-email&mt=8&pt=524675 or Android https://play.google.com/store/apps/details?id=com.github.android&referrer=utm_campaign%3Dnotification-email%26utm_medium%3Demail%26utm_source%3Dgithub.
You are receiving this because you commented.Message ID: @.***>
-- Bill Forster 15A Boundary Road Kelburn Wellington 6012 New Zealand +64 21 357 371 @.***
One more level of Kiwipete;
PerftFast(cr,1) = 48 Date/time is: Tue Jan 25 07:47:57 2022 PerftFast(cr,2) = 2039 Date/time is: Tue Jan 25 07:47:57 2022 PerftFast(cr,3) = 97862 Date/time is: Tue Jan 25 07:47:57 2022 PerftFast(cr,4) = 4085603 Date/time is: Tue Jan 25 07:47:58 2022 PerftFast(cr,5) = 193690690 Date/time is: Tue Jan 25 07:48:17 2022 PerftFast(cr,6) = 8031647685 Date/time is: Tue Jan 25 08:02:14 2022 PerftFast(cr,7) = 374190009323 Date/time is: Tue Jan 25 19:32:49 2022
On Mon, 24 Jan 2022 at 22:32, disservin @.***> wrote:
Hey thanks for the quick replay, your altered version works just fine, the comparison was done because I wanted to see the current move, mv std::cout << mv_text << std::enl; However sometimes I didnt get a move back but got "--". Which I thought is some kind of bug ? So I simply tried to skip that part. Great that perft confirmed the move generation. !
— Reply to this email directly, view it on GitHub https://github.com/billforsternz/thc-chess-library/issues/13#issuecomment-1019894503, or unsubscribe https://github.com/notifications/unsubscribe-auth/ABSQYSVV5DJ53QYGXXKB5OLUXUMBJANCNFSM5MTX4BAA . Triage notifications on the go with GitHub Mobile for iOS https://apps.apple.com/app/apple-store/id1477376905?ct=notification-email&mt=8&pt=524675 or Android https://play.google.com/store/apps/details?id=com.github.android&referrer=utm_campaign%3Dnotification-email%26utm_medium%3Demail%26utm_source%3Dgithub.
You are receiving this because you commented.Message ID: @.***>
-- Bill Forster 15A Boundary Road Kelburn Wellington 6012 New Zealand +64 21 357 371 @.***
Shouldnt that return 400 for depth 2 ? Always returns 4200 for me. Sorry if thats the wrong place to ask here. Read more about Perft on Chessprogramming Wiki `
`