Impossible perft question

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: Impossible perft question

Post by michiguel »

lucasart wrote:
michiguel wrote:
Sven Schüle wrote:
trojanfoe wrote:
lucasart wrote: (snipped)
I do not believe one second that Gaviota would have an incorrect perft(1) in a position that simple. Your FEN is incorrect!

Code: Select all

[d]1N6/6k1/8/8/7B/8/8/4K3 w - - 19 103
103 ???
The FEN was generated by taking a position in the normal starting position, and then making a random (legal) move. The number of moves made is also random so I believe the FEN is correct. What's wrong with having a move of 103?
Unfortunately I can confirm the wrong gaviota result. The output below is the same for the 32 and 64 bit versions of Gaviota 0.86 on Windows:

Code: Select all

Gaviota v0.86
Copyright (c) 2000-2013 Miguel A. Ballicora
There is NO WARRANTY of any kind
# mode = winboard/xboard
# Type 'screen' for a better output in console mode
# Type 'help' for a list of useful commands

setboard 1N6/6k1/8/8/7B/8/8/4K3 w - - 0 1
perft 1
depth 0: leaves:          1 accum:          1
depth 1: leaves:         10 accum:         11
seconds: 0.00
perftdiv 1
   -->   Nb8-c6           1
   -->   Ke1-f2           1
   -->   Ke1-e2           1
   -->   Ke1-f1           1
   -->   Nb8-d7           1
   -->   Ke1-d2           1
   -->   Bh4-d8           1
   -->   Bh4-e7           1
   -->   Bh4-g5           1
   -->   Bh4-f6           1
depth 1: leaves:         10
seconds: 0.02 nps: 500.00
Sven
Ha!!!! it is unbelievable that I am going to say... this is not a bug, it is a feature :-), but I should remove it from perft. :oops:

Gaviota rejects moves after being generated in the KBNvK endgame. In this case, moves where the king increments the distance with the other king (Kd1,Kd2), and moves where the B does not attack the opponent kings surroundings. The reason is because neither of those moves are good and it can be demonstrated that you will never need them. It is some sort of super hard pruning. With this feature and some others, Gaviota became extremely good at mating in this endgame, better than any other Adam and I tested (without TBs, of course).

This does not increase any elo, but it was fun to explore this endgame to its full capacity.

I really need to fix this, otherwise it screws perft completely and that is not good. Thanks for reporting it!

Miguel
PS: This is the code. During pre ordering of the moves, if the position is KBNK and the moves is !KBNK_nicemove(), the move is directly eliminated from the list.

Code: Select all

static int kingdist (SQUARE fr, SQUARE to);
static int taxidist (SQUARE fr, SQUARE to);
static int combidist(SQUARE a, SQUARE b) {return taxidist(a,b) + kingdist(a,b);}

#include "gtb-att.h"

#define FOURCORNERS U64(0x8100000000000081)

static bool_t 
KBNK_nicemove (POSITION *po, move_t mv)
{
	unsigned to = MV_TO(mv);
	unsigned fr = MV_FROM(mv);
	unsigned pc = MV_PC(mv);
	unsigned own = po->bi.occ[WH].n_all > 1? WH: BL;
	unsigned opp = Opp(own);
	BITBOARD occ = po->bi.occ[own].all;
	SQUARE 	 oppk = po->bi.occ[opp].king;
	BITBOARD kz = Reach[KING][oppk] | (U64(1) << oppk); /* king zone*/
	unsigned c = MV_COLOR(mv);
	unsigned mvc = Cidx(c);
	int 	 cd0 = combidist(fr,oppk);
	int 	 cd1 = combidist(to,oppk);

	return
		(mvc == opp) 							/* opponent king move */
	||	(0 != ((FOURCORNERS>>oppk) & U64(1))) 	/* opponent king in the corner */
	||	(KNIGHT == pc && (0 != (Reach[KNIGHT][to]&kz) || cd1 < cd0 )) /*N not attacking king zone, moving away*/
	||	(BISHOP == pc && 0 != (B_attacks(to,occ)&kz)) /*B not attacking king zone */
	||	(KING == pc && (cd1 == 4 || cd1 == 5 || cd1 <= cd0 )) /*king moving away*/
	;
}
That is a very creative idea. Thanks for sharing.

Can Gaviota find the mate in any KBNK endgame without any TB and without an yheuristic with this feature ? (by heuristic I mean a different PST to move the defending K in a corner of the colour of the B, for example).
No, Gaviota applies some other techniques for KBNK. I spend quite a bit of time on this to see how much I could improve it as a proof of concept.

What I mentioned above reduces the branching factor, which helps a lot. But, in the evaluation there are bonuses for
1) how close the kings are.
2) how far from the center the weak king is
3) how far from the main diagonal the weak king is (the one which has the opposite color of the bishop)
4) a special bonus for the knight in very specific squares.
a- the knight is in the second rank and the same color than the bishop
b - in the big center and the opposite color of the bishop (means it attacks squares from "a").
5) The eval does not compute 1 to 3 automatically. It evaluates if the opp king can escape to a square with a better score and average it.
6) After mores are generated, each move is played, the static score is computed, and score that is used for ordering.
7) The hashtable is considers mirrored positions.
8) Repetitions are draws in the second time, not the third. This is important to make sure it does not fool around wasting important moves
9) Certain moves are plainly rejected as I mentioned previously.

That is basically it.

With this, properly tuned, I managed to make Gaviota consistently mate in less than 50 moves against Gaviota+TBs using only 10,000 nodes / move. Not many engines can do that 100% of the time.

Miguel

If so it's really elegant. You solve the KBNK by means of better search rather than using eval heuristic.

DiscoCheck has no knowledge of KBNK and it stupidly searches all the moves and doesn't know in which corner to push the king. It uses general PST knowledge to push the king in a corner or an edge, but if the defendor chooses to go in a colour opposite colour to the B, it will take a lot of depth to find the mating line... And only when the mating line is found DC will start to play accurately... Quite pathetic to watch really
User avatar
trojanfoe
Posts: 65
Joined: Sun Jul 31, 2011 11:57 am
Location: Waterlooville, Hampshire, UK

Re: Impossible perft question

Post by trojanfoe »

Finally fixed the move generator bug. I wrote code to generate millions of random positions to compare ccore against critter at depth-1. This came to nothing. I then realized the correct approach was to generate all the positions, recursively, from the original failing perft position in order to find a position that fails at depth-1. This gave me this little peach:

[d]8/2p5/3p4/KP6/R1r2pPk/4P3/8/8 b - g3 0 3

I was failing to generate fxg3 due to my most recent "en-passant pinned" "fix". Sven was bang-on with his feeling of where the bug lay.

Many thanks to all.