perft moves list

Discussion of chess software programming and technical issues.

Moderator: Ras

User avatar
michiguel
Posts: 6401
Joined: Thu Mar 09, 2006 8:30 pm
Location: Chicago, Illinois, USA

Re: perft moves list

Post by michiguel »

stegemma wrote:Thanks, i try your engine too.

Maibe we can consider to define a perft standard, for such kind of output?

I think that it could help very much to have some kind of standard, because using that standard we can automate the engine perft testing, comparing our software with other stable engines.
That is perftdiv (read this somewhere, not my idea). In gaviota you get

Code: Select all

perftdiv 6
   -->    f2-f4     4890429
   -->    c2-c4     5866666
   -->    e2-e4     9771632
   -->    d2-d4     8879566
   -->    h2-h4     5385554
   -->    g2-g4     5239875
   -->    f2-f3     4404141
   -->    c2-c3     5417640
   -->    b2-b4     5293555
   -->    a2-a4     5363555
   -->    e2-e3     9726018
   -->    d2-d3     8073082
   -->    h2-h3     4463070
   -->    g2-g3     5346260
   -->    b2-b3     5310358
   -->    a2-a3     4463267
   -->   Ng1-f3     5723523
   -->   Nb1-c3     5708064
   -->   Ng1-h3     4877234
   -->   Nb1-a3     4856835
depth 6: leaves:  119060324
seconds: 33.18 nps: 3588315.97
perftdiv is the most useful tool to debug a generator.
Miguel
User avatar
stegemma
Posts: 859
Joined: Mon Aug 10, 2009 10:05 pm
Location: Italy
Full name: Stefano Gemma

Re: perft moves list

Post by stegemma »

JuLieN wrote:Congrats! ;) I'm glad I could help. I remember those days when I was working on the move generator, with the most bizarre bugs producing weird results...

You probably know them yet, but here are good perft positions to catch bugs, with their correct results:

http://www.albert.nu/programs/sharper/perft.asp
http://chessprogramming.wikispaces.com/Perft+Results
In fact the second position of the first link was the one that was so hard to debug for. The bug is very interesting. I use C++ classes to define almost all, in my new engine. I know that this is not a good solution, from a speed point of view, but i want to do something new, not the same old assembly stuffs. In the class clsMove i had the Execute and UnDo functions, that works the same for almost any piece. There was some switch to handle "strange" moves, like castling, promotion and en-passant. The UnDo function for any piece FIRST renew the eventually captured piece and then check for speciality of the move, to handle properly. All works fine for castling and enpassant but... for promotion i temporarily create a new clsPiece object of the right class (clsWhiteQueen, clsWhiteBishop and so on...) and substitute the clsPiece pointer in the pieces array. When promotion is undone, the standard UnDo take place then the new promoted piece is deleted and the old one (the pawn) will be moved to original position. In this extra work, a function MoveTo for the original pawn went be called... but this function moves the pawn from destination to source position... and in the destination now there are again the captured piece!!! So, when a promotion with capture went undone, the captured piece disappears :)

The solution? Just moving the positioning of the captured piece to destination square at the end of the UnDo function solves the problem. It's hardest to explain the bug than to solve it! ;)

Thanks again.
User avatar
stegemma
Posts: 859
Joined: Mon Aug 10, 2009 10:05 pm
Location: Italy
Full name: Stefano Gemma

Re: perft moves list

Post by stegemma »

PS: in this position:

"8/7p/p5pb/4k3/P1pPn3/8/P5PP/1rB2RK1 b - d3 0 28"

quick perft reports:

Quick Perft by H.G. Muller
Perft mode: No hashing, bulk counting in horizon nodes

perft(1)=32 ( 0.000 sec)

perft(2)=732 ( 0.000 sec)

perft(3)=20448 ( 0.000 sec)

perft(4)=439642 ( 0.007 sec)

perft(5)=12028429 ( 0.188 sec)

perft(6)=259505253 ( 3.763 sec)

but perft(1) should be 5, not 32... and my engine reports 4, missing the en-passant move in d3 to avoid check.
User avatar
sje
Posts: 4675
Joined: Mon Mar 13, 2006 7:43 pm

Re: perft moves list

Post by sje »

[d]

Code: Select all

[] empbulk 1
Kd5 1
Kd6 1
Ke6 1
Kxd4 1
cxd3 1
Depth: 1   Count: 5   Elapsed: 0.044  (113.636 Hz / 0.0088 s)
[] empbulk 2
Kd5 23
Kd6 24
Ke6 24
Kxd4 23
cxd3 23
Depth: 2   Count: 117   Elapsed: 0.04212  (2777.78 Hz / 0.00036 s)
[] empbulk 3
Kd5 672
Kd6 676
Ke6 682
Kxd4 639
cxd3 624
Depth: 3   Count: 3,293   Elapsed: 0.042846  (76856.6 Hz / 1.30112e-05 s)
[] empbulk 4
Kd5 13,428
Kd6 14,117
Ke6 14,151
Kxd4 13,030
cxd3 12,471
Depth: 4   Count: 67,197   Elapsed: 0.068405  (982340 Hz / 1.01798e-06 s)
[] empbulk 5
Kd5 382,530
Ke6 395,423
Kxd4 360,136
Kd6 401,106
cxd3 341,894
Depth: 5   Count: 1,881,089   Elapsed: 0.161573  (1.16423e+07 Hz / 8.58933e-08 s)
[] empbulk 6
Kxd4 7,438,869
Kd5 7,747,197
Ke6 8,232,156
Kd6 8,335,508
cxd3 6,879,553
Depth: 6   Count: 38,633,283   Elapsed: 3.13231  (1.23338e+07 Hz / 8.10779e-08 s)
[] empbulk 7
Kxd4 202,248,953
Kd5 216,135,695
Ke6 228,162,609
Kd6 233,877,684
cxd3 188,764,129
Depth: 7   Count: 1,069,189,070   Elapsed: 64.3411  (1.66175e+07 Hz / 6.01775e-08 s)
User avatar
hgm
Posts: 28390
Joined: Fri Mar 10, 2006 10:06 am
Location: Amsterdam
Full name: H G Muller

Re: perft moves list

Post by hgm »

stegemma wrote:PS: in this position:

"8/7p/p5pb/4k3/P1pPn3/8/P5PP/1rB2RK1 b - d3 0 28"

quick perft reports:

Quick Perft by H.G. Muller
Perft mode: No hashing, bulk counting in horizon nodes

perft(1)=32 ( 0.000 sec)

perft(2)=732 ( 0.000 sec)

perft(3)=20448 ( 0.000 sec)

perft(4)=439642 ( 0.007 sec)

perft(5)=12028429 ( 0.188 sec)

perft(6)=259505253 ( 3.763 sec)

but perft(1) should be 5, not 32... and my engine reports 4, missing the en-passant move in d3 to avoid check.
Hmm, I recently changed qperft to use another routine in the last ply, and this could mean I broke perft(1). I will check it out.
User avatar
stegemma
Posts: 859
Joined: Mon Aug 10, 2009 10:05 pm
Location: Italy
Full name: Stefano Gemma

Re: perft moves list

Post by stegemma »

Now the new Freccia engine seems ok. I post the pert fen positions that i've used. Are all derived from know one but i hope that they can be interesting. They can be directly copied and pasted to a C char* array:

Code: Select all

"rnbqkbnr/pppppppp/8/8/8/8/PPPPPPPP/RNBQKBNR w KQkq - 0 1",
  "20, 400, 8902, 197281, 4865609, 119060324, 3195901860",
"k7/8/K7/8/8/8/8/8 w - - 0 1",
  "3, 7, 35, 169, 1008, 4880, 31681, 179315",
"4k3/8/8/8/8/8/8/R3K2R w KQ - 0 1",
  "26, 112, 3189, 17945, 532933, 2788982, 84866591, 453607151",
"4k3/8/4K3/7Q/8/8/8/8 w - - 0 1",
  "26, 45, 1161, 3207, 86329, 309421, 8538589, 33697224",
"4k3/8/4K3/7N/8/7N/8/B7 w - - 0 1",
  "20, 49, 1051, 3522, 78939, 334571, 7750876, 36963298",
"4k3/8/4K3/7N/8/7N/PPPPPPPP/2B5 w - - 0 1",
  "26, 63, 1717, 5750, 159056, 722569, 20247320, 99274701",
"r3k2r/p1ppqpb1/bn2pnp1/3PN3/1p2P3/2N2Q1p/PPPBBPPP/R3K2R w KQkq -",
  "48, 2039, 97862, 4085603, 193690690",
"r3k2r/p1ppqpb1/bn1Ppnp1/4N3/1p2P3/2N2Q1p/PPPBBPPP/R3K2R b KQkq -",
  "41, 1991, 79551, 3835265, 151133066",
"r3k2r/p1ppqpb1/bn1Ppnp1/4N3/1p2P3/2N2Q2/PPPBBPpP/R3K2R w KQkq -",
  "47, 2301, 101608, 4744698, 210555622",
"r3k2r/p1Ppqpb1/bn2pnp1/4N3/1p2P3/2N2Q2/PPPBBPpP/R3K2R b KQkq -",
  "48, 2156, 97227, 4468960",
"r3k2r/8/8/8/8/8/8/R3K2R w KQkq -",
  "26, 568, 13744, 314346, 7594526",
"4k3/8/8/8/8/1r6/8/R3K2R w KQ -",
  "26, 449, 10878, 179619, 4511324",
"r3k2r/ppppNppp/8/8/8/8/PPPPnPPP/R3K2R w KQkq -",
  "28, 774, 21359, 578328, 15625345",
"r3k2r/p1ppqpb1/bn2pnp1/3PN3/1p2P3/2N2Q1p/PPPBBPPP/R4K1R b kq -"	,
  "43, 1855, 77887, 3377351, 139601450",
"1r2k2r/p1ppqpb1/bn2pnp1/3PN3/1p2P3/2N2Q1p/PPPBBPPP/R4K1R w k -"	,
  "45, 1956, 85453, 3619848, 158330435",
"8/3K4/2p5/p2b2r1/5k2/8/8/1q6 b - 1 67",
 "50, 279",
"8/7p/p5pb/4k3/P1pPn3/8/P5PP/1rB2RK1 b - d3 0 28",
  "5, 117, 3293, 67197, 1881089, 38633283, 1069189070",
"rnbqkb1r/ppppp1pp/7n/4Pp2/8/8/PPPP1PPP/RNBQKBNR w KQkq f6 0 3"		,
  "31, 570, 17546, 351806, 11139762, 244063299, 7930902498",
They are couples of strings: the first one is FEN and the second one contains the nodes count per any ply (it is not fixed, some position has deeper depth than other ones).
User avatar
stegemma
Posts: 859
Joined: Mon Aug 10, 2009 10:05 pm
Location: Italy
Full name: Stefano Gemma

Re: perft moves list

Post by stegemma »

michiguel wrote:
stegemma wrote:Thanks, i try your engine too.

Maibe we can consider to define a perft standard, for such kind of output?

I think that it could help very much to have some kind of standard, because using that standard we can automate the engine perft testing, comparing our software with other stable engines.
That is perftdiv (read this somewhere, not my idea). In gaviota you get

Code: Select all

perftdiv 6
   -->    f2-f4     4890429
   -->    c2-c4     5866666
   -->    e2-e4     9771632
   -->    d2-d4     8879566
   -->    h2-h4     5385554
   -->    g2-g4     5239875
   -->    f2-f3     4404141
   -->    c2-c3     5417640
   -->    b2-b4     5293555
   -->    a2-a4     5363555
   -->    e2-e3     9726018
   -->    d2-d3     8073082
   -->    h2-h3     4463070
   -->    g2-g3     5346260
   -->    b2-b3     5310358
   -->    a2-a3     4463267
   -->   Ng1-f3     5723523
   -->   Nb1-c3     5708064
   -->   Ng1-h3     4877234
   -->   Nb1-a3     4856835
depth 6: leaves:  119060324
seconds: 33.18 nps: 3588315.97
perftdiv is the most useful tool to debug a generator.
Miguel
perftdiv can be a good candidate for a standard. Maybe we can choose to standardize the output so that it is simpler to read from another engine?

In my case, i've simply compared nodes count by hand and that was enough... but doing that working at nigth could make me blind after hours of testing ;)

I would add perftdiv as a command to my engine, since now, in this format:

command:

perftdiv depth

gives this output:

move count
move count
...

where move is the short move notation (e1g1 instead of 00, f3e5 instead of Nf3xe5 and so on) and count is without any thousands separators (they are not portable, in Italy we use ., in USA they use , for sample).

If we all agree for this format, maybe we can help anybody else wants to write a new engine from scratch.
User avatar
stegemma
Posts: 859
Joined: Mon Aug 10, 2009 10:05 pm
Location: Italy
Full name: Stefano Gemma

Re: perft moves list

Post by stegemma »

hgm wrote:
stegemma wrote:PS: in this position:

"8/7p/p5pb/4k3/P1pPn3/8/P5PP/1rB2RK1 b - d3 0 28"

quick perft reports:

Quick Perft by H.G. Muller
Perft mode: No hashing, bulk counting in horizon nodes

perft(1)=32 ( 0.000 sec)
...
Hmm, I recently changed qperft to use another routine in the last ply, and this could mean I broke perft(1). I will check it out.
While you're debugging, maybe you can correct even this "non-bug":

perft 5 "4k3/8/8/8/8/2r3r1/8/R3K2R w KQ -"

I've sent you a message about this but maybe has been lost. This is not properly a bug, because the position is bad (black can't castle while there are KQ in the FEN) but perft maybe should notify "bad fen position" or compute the right nodes count, while it doesn't. Despite from that, you perft is very fast and usefull!!!
User avatar
hgm
Posts: 28390
Joined: Fri Mar 10, 2006 10:06 am
Location: Amsterdam
Full name: H G Muller

Re: perft moves list

Post by hgm »

Well, the most annoying thing in comparing perft counts to me always was that the moves are not in the same order. Another annoyance is that when you have a difference in the root count, do a single sub-division to find the move for which the count differs, and then do new perfts from the position after that move, the difference has often gone away. This makes higher-order sub-division necessary, but this tends to overflow you with so much output that comparison by hand becomes hard.

The way qperft now outputs the sub-divided counts israther convenient in this respect: you can write it to file, and then sort it alphabetically. This will use the ply-level as the primary sort key, and then sort the move sequences within that ply in a well-defined way. Doing the same for the output of the program-under-test should make it quite easy to spot the difference.
User avatar
Ajedrecista
Posts: 2126
Joined: Wed Jul 13, 2011 9:04 pm
Location: Madrid, Spain.

Re: perft moves list

Post by Ajedrecista »

Hello:

[d]

I can confirm Steven Edwards' results:

Code: Select all

JetChess 1.0.0.0 (hash = 64 MB).

Perft(1):
Total:                5
5   (move pathes after 1 half move).
Time: 0 ms.

Perft(2):
  1   c4*d3e         23
  2  ke5-d5          23
  3  ke5*d4          23
  4  ke5-d6          24
  5  ke5-e6          24
Total:              117
117   (move pathes after 2 half moves).
Time: 0 ms.

Perft(3):
  1   c4*d3e        624
  2  ke5-d5         672
  3  ke5*d4         639
  4  ke5-d6         676
  5  ke5-e6         682
Total:             3293
3,293   (move pathes after 3 half moves).
Time: 0 ms.

Perft(4):
  1   c4*d3e      12471
  2  ke5-d5       13428
  3  ke5*d4       13030
  4  ke5-d6       14117
  5  ke5-e6       14151
Total:            67197
67,197   (move pathes after 4 half moves).
Time: 9 ms.

Perft(5):
  1   c4*d3e     341894
  2  ke5-d5      382530
  3  ke5*d4      360136
  4  ke5-d6      401106
  5  ke5-e6      395423
Total:          1881089
1,881,089   (move pathes after 5 half moves).
Time: 27 ms.

Perft(6):
  1   c4*d3e    6879553
  2  ke5-d5     7747197
  3  ke5*d4     7438869
  4  ke5-d6     8335508
  5  ke5-e6     8232156
Total:         38633283
38,633,283   (move pathes after 6 half moves).
Time: 396 ms.

Perft(7):
  1   c4*d3e  188764129
  2  ke5-d5   216135695
  3  ke5*d4   202248953
  4  ke5-d6   233877684
  5  ke5-e6   228162609
Total:       1069189070
1,069,189,070   (move pathes after 7 half moves).
Time: 4.652 s.
I add Perft(8) and Perft(9):

Code: Select all

JetChess 1.0.0.0.

Perft(8) with 512 MB of hash:
  1   c4*d3e 3899646321
  2  ke5-d5  4505399674
  3  ke5*d4  4291215523
  4  ke5-d6  4947659966
  5  ke5-e6  4844580296
Total:      22488501780
22,488,501,780   (move pathes after 8 half moves).
Time: 49.087 s.

Perft(9) with 1024 MB of hash:
  1   c4*d3e 106718015882
  2  ke5-d5  123552363384
  3  ke5*d4  114933529736
  4  ke5-d6  136792876768
  5  ke5-e6  132978721727
Total:     614975507497
614,975,507,497   (move pathes after 9 half moves).
Time: 626.128 s.
These results should be correct; Stefano, I recommend you run Perft(8) and Perft(9) of this position for ensure that you have debugged your code successfully.

Regards from Spain.

Ajedrecista.