billjordanchess / Bitboard-Chess

Simple C++ chess playing program which uses bitboards
GNU General Public License v3.0
9 stars 2 forks source link

NextBit2() fix #2

Open braoult opened 9 months ago

braoult commented 9 months ago

I noticed in bitboard.cpp :

const BITBOARD debruijn64 = 0x07EDD5E59A4E28C2;

const int index64[64] = {
        63,  0, 58,  1, 59, 47, 53,  2,
        60, 39, 48, 27, 54, 33, 42,  3,
        61, 51, 37, 40, 49, 18, 28, 20,
        55, 30, 34, 11, 43, 14, 22,  4,
        62, 57, 46, 52, 38, 26, 32, 41,
        50, 36, 17, 19, 29, 10, 13, 21,
        56, 45, 25, 31, 35, 16,  9, 12,
        44, 24, 15,  8, 23,  7,  6,  5
};

[...]

int NextBit2(BITBOARD bb)//number 2  crashed
{
        if(bb==0) return 0;
        const BITBOARD debruijn64 = (unsigned char)(0x03f79d71b4cb0a89);
        //   assert (bb != 0);
        return index64[((bb ^ (bb-1)) * debruijn64) >> 58];
}

The comment on NextBit2() indicates you did not get it to work...

To fix it :

So the function could be rewritten as:

int NextBit64(BITBOARD bb)
{
        return index64[  (  (bb & -b) * debruijn64 ) >> 58 ];
}
billjordanchess commented 9 months ago

Hi Bruno,

Thanks for your feedback.

I commented out the

assert (bb != 0);

line because

if(bb==0) return 0;

seemed to run faster.

At some stage I will test your suggestion.

Interesting.

Bill Jordan

On Sun, Feb 4, 2024 at 7:00 PM Bruno Raoult @.***> wrote:

I noticed in bitboard.cpp :

const BITBOARD debruijn64 = 0x07EDD5E59A4E28C2; const int index64[64] = { 63, 0, 58, 1, 59, 47, 53, 2, 60, 39, 48, 27, 54, 33, 42, 3, 61, 51, 37, 40, 49, 18, 28, 20, 55, 30, 34, 11, 43, 14, 22, 4, 62, 57, 46, 52, 38, 26, 32, 41, 50, 36, 17, 19, 29, 10, 13, 21, 56, 45, 25, 31, 35, 16, 9, 12, 44, 24, 15, 8, 23, 7, 6, 5 };

[...] int NextBit2(BITBOARD bb)//number 2 crashed { if(bb==0) return 0; const BITBOARD debruijn64 = (unsigned char)(0x03f79d71b4cb0a89); // assert (bb != 0); return index64[((bb ^ (bb-1)) * debruijn64) >> 58]; }

The comment on NextBit2() indicates you did not get it to work...

To fix it :

  • Delete the (wrong) const BITBOARD line inside NextBit2() (the global one is the correct one for the index64 table used). Beside the wrong value, the (unsigned char) would have failed anyway.
  • The return should use (bb & -bb) instead of (bb ^ (bb-1)) , maybe a faulty copy/paste from NextBit() here ?

So the corresponding function could be rewritten as:

int NextBit64(BITBOARD bb) { return index64[ ( (bb & -b) * debruijn64 ) >> 58 ]; }

— Reply to this email directly, view it on GitHub https://github.com/billjordanchess/Bitboard-Chess/issues/2, or unsubscribe https://github.com/notifications/unsubscribe-auth/AMZ45CZHV6VPUH2EUS6QT2TYR5BJ5AVCNFSM6AAAAABCYVYBGKVHI2DSMVQWIX3LMV43ASLTON2WKOZSGEYTMOJVGY2DQNI . You are receiving this because you are subscribed to this thread.Message ID: @.***>

braoult commented 9 months ago

I commented out the assert (bb != 0); line because if(bb==0) return 0; seemed to run faster.

In fact, you cannot do that, these two statements are unrelated: While assert() displays a message and aborts the program, return 0 returns a valid bit position (when lsb bit is set - bit 0 or bit 1, depending on convention used :

We should have, for bit 0 set: NextBit(1) == NextBit2(1) == 0, which is different from calling them with no bit set: NextBit(0) and NextBit2(0) have undefined behavior (you cannot call these functions with zero).

If you look at your gen.cpp code, you will see you correctly test for i ≠ 0 before calling NextBit(i) (I added the comments):

        [...]
        // loop on all b1 set bits, for example if b1== 0x5 (binary 101), we will get 0 and 2
        while(b1)                           // while b1 is non-zero
        {
                sq = NextBit(b1);           // position of next bit set (0-63)
                b1 &= not_mask[sq];         // unset bit at position sq
                [ ...]
        }
        [...]

FYI, assert() is simply disabled (no code is generated) if you set the NDEBUG macro, so it has no effect on performance when you release the software.