Computer Chess Club Archives


Search

Terms

Messages

Subject: Re: checks in qsearch

Author: Vincent Diepeveen

Date: 11:34:53 10/29/02

Go up one level in this thread


On October 29, 2002 at 12:15:29, Uri Blass wrote:

>On October 29, 2002 at 11:52:18, Vincent Diepeveen wrote:
>
>>On October 29, 2002 at 06:46:18, Uri Blass wrote:
>>
>>>On October 29, 2002 at 04:26:38, Dave Gomboc wrote:
>>>
>>>>On October 29, 2002 at 04:05:14, Uri Blass wrote:
>>>>
>>>>>It is faster to have a special function that generate the moves and calculate
>>>>>moves that are checks.
>>>>>
>>>>>The point is that a lot of moves are from the same from square so I do not need
>>>>>to check if the from square is in the same direction with the king if I do it in
>>>>>that way.
>>>>
>>>>You may want to work outwards from the king.
>>>>
>>>>Dave
>>>
>>>Yes
>>>
>>>I think that it is a good idea in order to detect fast cases when I do not need
>>>to check the from square for all moves.
>>>
>>>If there is no piece that pseudoattack the king from all directions then it
>>>means that the only possible checks are based on the to square.
>>>
>>>I already do it when I update my pin arrays but I did not think about it when I
>>>generated my function to detect checks in the first plies of the qsearch.
>>>
>>>Note that my pin array can also be optimized.
>>>Today movei knows only the pinned pieces of the side to move and I believe that
>>>it is better to know the pinned pieces of both sides and to update them.
>>>
>>>Uri
>>
>>You could go for something cheap to detect checks in qsearch
>>and just see whether the 'to' square possibly attacks the king
>>square, only after that call a function.
>>
>>if( quickchecktable[piece][63+kingsq-to]
>> && slowcheck(piece,to,kingsq) )
>>  check = true; ...
>
>In that case I may miss checks that are not done by the piece that moved.

You are concerned about xray checks?

In DIEP i do things like that, but i don't know many engines
which do checks in qsearch which do them. Note that i do
unlimited checks in the qsearch for like 32
ply in a row or so (my stackdepth of qsearch currently is 32 ply
i did see no reason yet to make that more).

In any case, here is how i do things in qsearch, but i have to
warn you that it's very slow if you want to get a million
nodes a second :)

Note that you see i'm using incremental attack tables too.

For a number of years i could do without incremental attack tables
by simply only using them in evaluation a lot and quite a bit less
in move ordering.

>I still have ways to improve the speed without missing checks.

In case you want to do *all* checks, then you might want to use
attacktables too.

Note that i simply generate all moves in qsearch. Total move generation
all together is like 0.6% system time anyway.

Then i can do all moves from which i gamble that they are making my
search more quiet. With big evaluation not necessarily captures and
checks are the only moves that can modify evaluation a lot.

>Note that I cannot use the difference in the squares to decide if a rook pseudo
>attack the king because the difference between h2 and a3 is the same as the
>difference between a3 and b3.

but it's very fast to use such a small table that eliminates already the
vaste majority.

But indeed i also got rid of that primitive table and use a bigger table
now. The primitive table works great however for programs that want to
get a million nodes a second and extend check evasions (so we do not
talk about qsearch here but about normal search where of course
calling a function to detect whether you are in check is way way too
slow).

Here is some code from DIEP hoping you will have a look at it:

    /* Eerst controleren op schaak */
    if( piece != king && looprichting[piece][t][OpKing]
     && ScanAttack(side,piece,t,OpKing) ) {
      nt->zet |= move_checks;
    }

    /* Aftrekschaak */
    if( (AttM[f]&(ctlB|ctlR|ctlQ)) ) {
      if( ((AttM[f]&ctlB) && looprichting[bishop][f][OpKing]
           && ScanXrayAttack(side,bishop,f,OpKing))
       || ((AttM[f]&ctlR) && looprichting[rook][f][OpKing]
           && ScanXrayAttack(side,rook,f,OpKing))
       || ((AttM[f]&ctlQ) && looprichting[queen][f][OpKing]
           && ScanXrayAttack(side,queen,f,OpKing)) ) {
        int bb,bc,bd,be;
        bb = board[t];
        bc = color[t];
        be = snelbord[f];
        bd = snelbord[t];
        snelbord[f] = 0;
        snelbord[t] = 7;
        board[f] = 0;
        color[f] = neutral;
        board[t] = 7;  /* zodat schaakje niet van het stuk zelf is */
        color[t] = xside;
        if( SqAttackedBySide(OpKing,side) ) {
          nt->zet |= move_checks;
          aftrekschaak = 1;
     /*     #if ForwardPruning
          nt->zet |= move_noprune;
          #endif*/
        }
        board[f] = piece;
        color[f] = side;
        board[t] = bb;
        color[t] = bc;
        snelbord[f] = be;
        snelbord[t] = bd;
      }
    }



>I still can use the difference in the squares to decide that there are no case
>in a lot of cases so maybe it is a good idea to have table like you suggest.
>
>Uri



This page took 0.01 seconds to execute

Last modified: Thu, 15 Apr 21 08:11:13 -0700

Current Computer Chess Club Forums at Talkchess. This site by Sean Mintz.