public static UInt64 rookAttacks(UInt64 occ, int s) { UInt64 binaryS = bitMask[s]; UInt64 possibilitiesHorizontal = (occ - 2 * binaryS) ^ BitOps.ReverseBytes(BitOps.ReverseBytes(occ) - 2 * BitOps.ReverseBytes(binaryS)); UInt64 possibilitiesVertical = ((occ & FilesBoard[s % 8]) - (2 * binaryS)) ^ BitOps.ReverseBytes(BitOps.ReverseBytes(occ & FilesBoard[s % 8]) - (2 * BitOps.ReverseBytes(binaryS))); return((possibilitiesHorizontal & RanksBoard[s / 8]) | (possibilitiesVertical & FilesBoard[s % 8])); }
public static UInt64 GetKingAttacks(UInt64 king) { UInt64 attacks = BitOps.OneStepEast(king) | BitOps.OneStepWest(king); king |= attacks; attacks |= BitOps.OneStepNorth(king) | BitOps.OneStepSouth(king); return(attacks); }
private static UInt64 GetPawnsAbleToSinglePush(bool isPlayer, UInt64 pawns, UInt64 empty) { if (isPlayer) { return(BitOps.OneStepSouth(empty) & pawns); } else { return(BitOps.OneStepNorth(empty) & pawns); } }
private static UInt64 GetWestAttacks(bool isPlayer, UInt64 pawns) { if (isPlayer) { return(BitOps.OneStepNorthWest(pawns)); } else { return(BitOps.OneStepSouthWest(pawns)); } }
private static UInt64 GetSinglePushTargets(bool isPlayer, UInt64 pawns, UInt64 empty) { if (isPlayer) { return(BitOps.OneStepNorth(pawns) & empty); } else { return(BitOps.OneStepSouth(pawns) & empty); } }
internal static UInt64 GetAllTargets(UInt64 knights, bool pieceColor, Board board) { UInt64 targets = 0UL; while (knights != 0) { // accede all'array di mosse precalcolate cercando il primo bit attivo all'interno della Board targets |= KnightAttacks[(BitOps.BitScanForwardReset(ref knights))]; } return(targets & ~board.GetColorPieces(pieceColor)); }
/* * West Nort NoWe NoEa * . . . . . . . . . . . 1 . . . . . . . . . . . . . . . . . . . 1 * . . . . . . . . . . . 1 . . . . 1 . . . . . . . . . . . . . 1 . * . . . . . . . . . . . 1 . . . . . 1 . . . . . . . . . . . 1 . . * . . . . . . . . . . . 1 . . . . . . 1 . . . . . . . . . 1 . . . * 1 1 1 R . . . . . . . R . . . . . . . B . . . . . . . B . . . . * . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . * . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . * . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . */ private static UInt64 getNegativeRayAttacks(UInt64 occupied, int rayDir, byte square) { UInt64 attacks = rayAttacks[rayDir, square]; UInt64 blocker = attacks & occupied; if (blocker != 0UL) { square = BitOps.bitScanReverse(blocker); attacks ^= rayAttacks[rayDir, square]; } return(attacks); }
private static UInt64 GetPawnsAbleToDoublePush(bool isPlayer, UInt64 pawns, UInt64 empty) { if (isPlayer) { UInt64 emptyRank3 = BitOps.OneStepSouth(empty & Constants.Ranks.Four) & empty; return(GetPawnsAbleToSinglePush(isPlayer, pawns, emptyRank3)); } else { UInt64 emptyRank6 = BitOps.OneStepNorth(empty & Constants.Ranks.Six) & empty; return(GetPawnsAbleToSinglePush(isPlayer, pawns, emptyRank6)); } }
private static UInt64 GetDoublePushTargets(bool isPlayer, UInt64 pawns, UInt64 empty) { UInt64 singlePush = GetSinglePushTargets(isPlayer, pawns, empty); if (isPlayer) { return(BitOps.OneStepNorth(singlePush) & empty & Constants.Ranks.Four); } else { return(BitOps.OneStepSouth(singlePush) & empty & Constants.Ranks.Five); } }
private static UInt64 GetKnightAttacks(UInt64 knights) { UInt64 west, east, attacks; east = BitOps.OneStepEast(knights); west = BitOps.OneStepWest(knights); attacks = (east | west) << 16; attacks |= (east | west) >> 16; east = BitOps.OneStepEast(east); west = BitOps.OneStepWest(west); attacks |= (east | west) << 8; attacks |= (east | west) >> 8; return(attacks); }
//unused now because there is a running total of totalWorth public int getTotalWorth() { //Player has negative score. Is there any point including the kings here? They will always cancel return(BitOps.BitCountWegner(BP) * Constants.VALUE_PAWN + BitOps.BitCountWegner(BN) * Constants.VALUE_KNIGHT + BitOps.BitCountWegner(BB) * Constants.VALUE_BISHOP + BitOps.BitCountWegner(BR) * Constants.VALUE_ROOK + BitOps.BitCountWegner(BQ) * Constants.VALUE_QUEEN + BitOps.BitCountWegner(BK) * Constants.VALUE_KING - BitOps.BitCountWegner(WP) * Constants.VALUE_PAWN - BitOps.BitCountWegner(WN) * Constants.VALUE_KNIGHT - BitOps.BitCountWegner(WB) * Constants.VALUE_BISHOP - BitOps.BitCountWegner(WR) * Constants.VALUE_ROOK - BitOps.BitCountWegner(WQ) * Constants.VALUE_QUEEN - BitOps.BitCountWegner(WK) * Constants.VALUE_KING); }
internal static UInt64 GetAllTargets(UInt64 king, bool pieceColor, Board board) { UInt64 kingMoves = KingAttacks[(BitOps.bitScanForward(king))]; //Cannot castle if already castled or is in check UInt64 empty; if (pieceColor && !board.playerHasCastled && !board.isCheck) { empty = board.GetEmptySquares(); //Right castle if (BitOps.IsBitSet(empty, 61) && BitOps.IsBitSet(empty, 62) && BitOps.IsBitSet(board.WR, 63)) { kingMoves |= (1UL << 62); } //Left castle else if (BitOps.IsBitSet(empty, 59) && BitOps.IsBitSet(empty, 58) && BitOps.IsBitSet(empty, 57) && BitOps.IsBitSet(board.WR, 56)) { kingMoves |= (1UL << 58); } } else if (!pieceColor && !board.computerHasCastled && !board.isCheck) { empty = board.GetEmptySquares(); //Right castle if (BitOps.IsBitSet(empty, 5) && BitOps.IsBitSet(empty, 6) && BitOps.IsBitSet(board.BR, 7)) { kingMoves |= (1UL << 6); } //Left castle else if (BitOps.IsBitSet(empty, 3) && BitOps.IsBitSet(empty, 2) && BitOps.IsBitSet(empty, 1) && BitOps.IsBitSet(board.BR, 0)) { kingMoves |= (1UL << 2); } } return(kingMoves & ~board.GetColorPieces(pieceColor)); }
//public static int counter = 0; public static void zobristFillArray() { Random rand = new Random(); for (int color = 0; color < 2; color++) { for (int pieceType = 0; pieceType < 6; pieceType++) { for (int square = 0; square < 64; square++) { zArray[color, pieceType, square] = BitOps.randomUInt64(rand); } } } for (int i = 0; i < 2; i++) { zCastle[i] = BitOps.randomUInt64(rand); } for (int i = 0; i < Algorithms.MAX_PLY; i++) { zDepth[i] = BitOps.randomUInt64(rand); } zBlackMove = BitOps.randomUInt64(rand); }
public static UInt64 bishopAttacks(UInt64 occ, int s) { UInt64 binaryS = bitMask[s]; UInt64 possibilitiesDiagonal = ((occ & DiagonalBoard[(s / 8) + (s % 8)]) - (2 * binaryS)) ^ BitOps.ReverseBytes(BitOps.ReverseBytes(occ & DiagonalBoard[(s / 8) + (s % 8)]) - (2 * BitOps.ReverseBytes(binaryS))); UInt64 possibilitiesAntiDiagonal = ((occ & AntiDiagonalBoard[(s / 8) + 7 - (s % 8)]) - (2 * binaryS)) ^ BitOps.ReverseBytes(BitOps.ReverseBytes(occ & AntiDiagonalBoard[(s / 8) + 7 - (s % 8)]) - (2 * BitOps.ReverseBytes(binaryS))); return((possibilitiesDiagonal & DiagonalBoard[(s / 8) + (s % 8)]) | (possibilitiesAntiDiagonal & AntiDiagonalBoard[(s / 8) + 7 - (s % 8)])); }
public short getTotalScore() { if (isCheckmate) { return(PlayersTurn ? (short)(-Constants.MATE_SCORE) : (short)Constants.MATE_SCORE); } if (isStalemate) { return(0); } UInt64 piece; int sq; //white is the maximizer short score = (short)(whiteWorth - blackWorth); //Getting a relative attack score for all possible captures on a board like this is a bad idea for 2 reasons; //1. It forces us to calculate the opponents pseudoMoves to get an approx even score, which is inaccurate because it is not their turn. //2. It does not consider the order of captures. //Both problems solved by Algorithm.Quint, which looks further into the game tree for capture moves only. //float attackScore = 0; //foreach (Move move in LegalMoves) // attackScore += (int)move.takenType - (int)((decimal)move.pieceType/(decimal)100); //foreach (Move move in opponentsPseudoMoves) // attackScore -= (int)move.takenType - (int)((decimal)move.pieceType / (decimal)100); short positionalScore = 0; //Pawns piece = BP; while (piece != 0) { sq = BitOps.BitScanForwardReset(ref piece); positionalScore += PawnTable[sq]; } piece = WP; while (piece != 0) { sq = BitOps.BitScanForwardReset(ref piece); positionalScore -= PawnTable[Mirror[sq]]; } //Knights piece = BN; while (piece != 0) { sq = BitOps.BitScanForwardReset(ref piece); positionalScore += KnightTable[sq]; } piece = WN; while (piece != 0) { sq = BitOps.BitScanForwardReset(ref piece); positionalScore -= KnightTable[Mirror[sq]]; } //Bishops piece = BB; while (piece != 0) { sq = BitOps.BitScanForwardReset(ref piece); positionalScore += BishopTable[sq]; } piece = WB; while (piece != 0) { sq = BitOps.BitScanForwardReset(ref piece); positionalScore -= BishopTable[Mirror[sq]]; } //Rooks piece = BR; while (piece != 0) { sq = BitOps.BitScanForwardReset(ref piece); positionalScore += RookTable[sq]; } piece = WR; while (piece != 0) { sq = BitOps.BitScanForwardReset(ref piece); positionalScore -= RookTable[Mirror[sq]]; } //King sq = blackKingIndex; if (blackWorth <= ENDGAME_MAT) { positionalScore += KingE[sq]; } else { positionalScore += KingO[sq]; } sq = whiteKingIndex; if (whiteWorth <= ENDGAME_MAT) { positionalScore -= KingE[Mirror[sq]]; } else { positionalScore -= KingO[Mirror[sq]]; } //score += (short)(POSITIONAL_WEIGHT * positionalScore); //pce = wP; //for (pceNum = 0; pceNum < pos->pceNum[pce]; ++pceNum) //{ // sq = pos->pList[pce][pceNum]; // ASSERT(SqOnBoard(sq)); // ASSERT(SQ64(sq) >= 0 && SQ64(sq) <= 63); // score += PawnTable[SQ64(sq)]; // if ((IsolatedMask[SQ64(sq)] & pos->pawns[WHITE]) == 0) // { // //printf("wP Iso:%s\n",PrSq(sq)); // score += PawnIsolated; // } // if ((WhitePassedMask[SQ64(sq)] & pos->pawns[BLACK]) == 0) // { // //printf("wP Passed:%s\n",PrSq(sq)); // score += PawnPassed[RanksBrd[sq]]; // } //} //pce = bP; //for (pceNum = 0; pceNum < pos->pceNum[pce]; ++pceNum) //{ // sq = pos->pList[pce][pceNum]; // ASSERT(SqOnBoard(sq)); // ASSERT(MIRROR64(SQ64(sq)) >= 0 && MIRROR64(SQ64(sq)) <= 63); // score -= PawnTable[MIRROR64(SQ64(sq))]; // if ((IsolatedMask[SQ64(sq)] & pos->pawns[BLACK]) == 0) // { // //printf("bP Iso:%s\n",PrSq(sq)); // score -= PawnIsolated; // } // if ((BlackPassedMask[SQ64(sq)] & pos->pawns[WHITE]) == 0) // { // //printf("bP Passed:%s\n",PrSq(sq)); // score -= PawnPassed[7 - RanksBrd[sq]]; // } //} //pce = wN; //for (pceNum = 0; pceNum < pos->pceNum[pce]; ++pceNum) //{ // sq = pos->pList[pce][pceNum]; // ASSERT(SqOnBoard(sq)); // ASSERT(SQ64(sq) >= 0 && SQ64(sq) <= 63); // score += KnightTable[SQ64(sq)]; //} //pce = bN; //for (pceNum = 0; pceNum < pos->pceNum[pce]; ++pceNum) //{ // sq = pos->pList[pce][pceNum]; // ASSERT(SqOnBoard(sq)); // ASSERT(MIRROR64(SQ64(sq)) >= 0 && MIRROR64(SQ64(sq)) <= 63); // score -= KnightTable[MIRROR64(SQ64(sq))]; //} //pce = wB; //for (pceNum = 0; pceNum < pos->pceNum[pce]; ++pceNum) //{ // sq = pos->pList[pce][pceNum]; // ASSERT(SqOnBoard(sq)); // ASSERT(SQ64(sq) >= 0 && SQ64(sq) <= 63); // score += BishopTable[SQ64(sq)]; //} //pce = bB; //for (pceNum = 0; pceNum < pos->pceNum[pce]; ++pceNum) //{ // sq = pos->pList[pce][pceNum]; // ASSERT(SqOnBoard(sq)); // ASSERT(MIRROR64(SQ64(sq)) >= 0 && MIRROR64(SQ64(sq)) <= 63); // score -= BishopTable[MIRROR64(SQ64(sq))]; //} //pce = wR; //for (pceNum = 0; pceNum < pos->pceNum[pce]; ++pceNum) //{ // sq = pos->pList[pce][pceNum]; // ASSERT(SqOnBoard(sq)); // ASSERT(SQ64(sq) >= 0 && SQ64(sq) <= 63); // score += RookTable[SQ64(sq)]; // ASSERT(FileRankValid(FilesBrd[sq])); // if (!(pos->pawns[BOTH] & FileBBMask[FilesBrd[sq]])) // { // score += RookOpenFile; // } // else if (!(pos->pawns[WHITE] & FileBBMask[FilesBrd[sq]])) // { // score += RookSemiOpenFile; // } //} //pce = bR; //for (pceNum = 0; pceNum < pos->pceNum[pce]; ++pceNum) //{ // sq = pos->pList[pce][pceNum]; // ASSERT(SqOnBoard(sq)); // ASSERT(MIRROR64(SQ64(sq)) >= 0 && MIRROR64(SQ64(sq)) <= 63); // score -= RookTable[MIRROR64(SQ64(sq))]; // ASSERT(FileRankValid(FilesBrd[sq])); // if (!(pos->pawns[BOTH] & FileBBMask[FilesBrd[sq]])) // { // score -= RookOpenFile; // } // else if (!(pos->pawns[BLACK] & FileBBMask[FilesBrd[sq]])) // { // score -= RookSemiOpenFile; // } //} //pce = wQ; //for (pceNum = 0; pceNum < pos->pceNum[pce]; ++pceNum) //{ // sq = pos->pList[pce][pceNum]; // ASSERT(SqOnBoard(sq)); // ASSERT(SQ64(sq) >= 0 && SQ64(sq) <= 63); // ASSERT(FileRankValid(FilesBrd[sq])); // if (!(pos->pawns[BOTH] & FileBBMask[FilesBrd[sq]])) // { // score += QueenOpenFile; // } // else if (!(pos->pawns[WHITE] & FileBBMask[FilesBrd[sq]])) // { // score += QueenSemiOpenFile; // } //} //pce = bQ; //for (pceNum = 0; pceNum < pos->pceNum[pce]; ++pceNum) //{ // sq = pos->pList[pce][pceNum]; // ASSERT(SqOnBoard(sq)); // ASSERT(SQ64(sq) >= 0 && SQ64(sq) <= 63); // ASSERT(FileRankValid(FilesBrd[sq])); // if (!(pos->pawns[BOTH] & FileBBMask[FilesBrd[sq]])) // { // score -= QueenOpenFile; // } // else if (!(pos->pawns[BLACK] & FileBBMask[FilesBrd[sq]])) // { // score -= QueenSemiOpenFile; // } //} ////8/p6k/6p1/5p2/P4K2/8/5pB1/8 b - - 2 62 //pce = wK; //sq = pos->pList[pce][0]; //ASSERT(SqOnBoard(sq)); //ASSERT(SQ64(sq) >= 0 && SQ64(sq) <= 63); //if ((pos->material[BLACK] <= ENDGAME_MAT)) //{ // score += KingE[SQ64(sq)]; //} //else //{ // score += KingO[SQ64(sq)]; //} //pce = bK; //sq = pos->pList[pce][0]; //ASSERT(SqOnBoard(sq)); //ASSERT(MIRROR64(SQ64(sq)) >= 0 && MIRROR64(SQ64(sq)) <= 63); //if ((pos->material[WHITE] <= ENDGAME_MAT)) //{ // score -= KingE[MIRROR64(SQ64(sq))]; //} //else //{ // score -= KingO[MIRROR64(SQ64(sq))]; //} //if (pos->pceNum[wB] >= 2) score += BishopPair; //if (pos->pceNum[bB] >= 2) score -= BishopPair; if (isCheck) { score += PlayersTurn ? (short)-Constants.CHECK_BONUS : Constants.CHECK_BONUS; } return(score); }
public static void initRayAttacks() { UInt64 rayAttack; for (byte i = 0; i < 64; i++) { UInt64 square = 1UL << i; //nort rayAttack = BitOps.OneStepNorth(square); rayAttack |= BitOps.OneStepNorth(rayAttack); rayAttack |= BitOps.OneStepNorth(rayAttack); rayAttack |= BitOps.OneStepNorth(rayAttack); rayAttack |= BitOps.OneStepNorth(rayAttack); rayAttack |= BitOps.OneStepNorth(rayAttack); rayAttack |= BitOps.OneStepNorth(rayAttack); rayAttacks[0, i] = rayAttack; //sout rayAttack = BitOps.OneStepSouth(square); rayAttack |= BitOps.OneStepSouth(rayAttack); rayAttack |= BitOps.OneStepSouth(rayAttack); rayAttack |= BitOps.OneStepSouth(rayAttack); rayAttack |= BitOps.OneStepSouth(rayAttack); rayAttack |= BitOps.OneStepSouth(rayAttack); rayAttack |= BitOps.OneStepSouth(rayAttack); rayAttacks[1, i] = rayAttack; //east rayAttack = BitOps.OneStepEast(square); rayAttack |= BitOps.OneStepEast(rayAttack); rayAttack |= BitOps.OneStepEast(rayAttack); rayAttack |= BitOps.OneStepEast(rayAttack); rayAttack |= BitOps.OneStepEast(rayAttack); rayAttack |= BitOps.OneStepEast(rayAttack); rayAttack |= BitOps.OneStepEast(rayAttack); rayAttacks[2, i] = rayAttack; //west rayAttack = BitOps.OneStepWest(square); rayAttack |= BitOps.OneStepWest(rayAttack); rayAttack |= BitOps.OneStepWest(rayAttack); rayAttack |= BitOps.OneStepWest(rayAttack); rayAttack |= BitOps.OneStepWest(rayAttack); rayAttack |= BitOps.OneStepWest(rayAttack); rayAttack |= BitOps.OneStepWest(rayAttack); rayAttacks[3, i] = rayAttack; //noEa rayAttack = BitOps.OneStepNorthEast(square); rayAttack |= BitOps.OneStepNorthEast(rayAttack); rayAttack |= BitOps.OneStepNorthEast(rayAttack); rayAttack |= BitOps.OneStepNorthEast(rayAttack); rayAttack |= BitOps.OneStepNorthEast(rayAttack); rayAttack |= BitOps.OneStepNorthEast(rayAttack); rayAttack |= BitOps.OneStepNorthEast(rayAttack); rayAttacks[4, i] = rayAttack; //soWe rayAttack = BitOps.OneStepSouthWest(square); rayAttack |= BitOps.OneStepSouthWest(rayAttack); rayAttack |= BitOps.OneStepSouthWest(rayAttack); rayAttack |= BitOps.OneStepSouthWest(rayAttack); rayAttack |= BitOps.OneStepSouthWest(rayAttack); rayAttack |= BitOps.OneStepSouthWest(rayAttack); rayAttack |= BitOps.OneStepSouthWest(rayAttack); rayAttacks[5, i] = rayAttack; //noWe rayAttack = BitOps.OneStepNorthWest(square); rayAttack |= BitOps.OneStepNorthWest(rayAttack); rayAttack |= BitOps.OneStepNorthWest(rayAttack); rayAttack |= BitOps.OneStepNorthWest(rayAttack); rayAttack |= BitOps.OneStepNorthWest(rayAttack); rayAttack |= BitOps.OneStepNorthWest(rayAttack); rayAttack |= BitOps.OneStepNorthWest(rayAttack); rayAttacks[6, i] = rayAttack; //soEa rayAttack = BitOps.OneStepSouthEast(square); rayAttack |= BitOps.OneStepSouthEast(rayAttack); rayAttack |= BitOps.OneStepSouthEast(rayAttack); rayAttack |= BitOps.OneStepSouthEast(rayAttack); rayAttack |= BitOps.OneStepSouthEast(rayAttack); rayAttack |= BitOps.OneStepSouthEast(rayAttack); rayAttack |= BitOps.OneStepSouthEast(rayAttack); rayAttacks[7, i] = rayAttack; } }
public static void initmagicmoves() { int i; //for bitscans : //initmagicmoves_bitpos64_database[(x*0x07EDD5E59A4E28C2UL)>>58] int[] initmagicmoves_bitpos64_database = new int[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 }; #if PERFECT_MAGIC_HASH for (i = 0; i < 1428; i++) { magicmovesbdb[i] = 0UL; } for (i = 0; i < 4900; i++) { magicmovesrdb[i] = 0UL; } #endif //Bishops for (i = 0; i < 64; i++) { int[] squares = new int[64]; int numsquares = 0; UInt64 temp = magicmoves_b_mask[i]; while (temp != 0UL) { int bitCount = BitOps.BitCountWegner(temp); squares[numsquares++] = bitCount; BitOps.BitScanForwardReset(ref temp); //UInt64 bit = temp & -temp; //squares[numsquares++] = initmagicmoves_bitpos64_database[(bit * 0x07EDD5E59A4E28C2UL) >> 58]; //temp ^= bit; } for (temp = 0; temp < (1UL << numsquares); temp++) { UInt64 tempocc = initmagicmoves_occ(squares, numsquares, temp); #if !PERFECT_MAGIC_HASH #if !VARIABLE_SHIFT magicmovesbdb[squares[i], Convert.ToInt32((tempocc * magicmoves_b_magics[squares[i]]) >> 55)] = initmagicmoves_Bmoves(i, tempocc); #else magicmovesbdb[squares[i], Convert.ToInt32((tempocc * magicmoves_b_magics[squares[i]]) >> magicmoves_b_shift[squares[i]])] = initmagicmoves_Bmoves(i, tempocc); #endif #else UInt64 moves = initmagicmoves_Bmoves(i, tempocc); #if !VARIABLE_SHIFT UInt64 index = ((tempocc * magicmoves_b_magics[i]) >> 55); #else UInt64 index = ((tempocc * magicmoves_b_magics[i]) >> magicmoves_b_shift[square]); #endif for (ushort j = 0; j < 1428; j++) { if (~magicmovesbdb[j] != 0UL) { magicmovesbdb[j] = moves; magicmoves_b_indices[i, Convert.ToInt32(index)] = j; break; } else if (magicmovesbdb[j] == moves) { magicmoves_b_indices[i, Convert.ToInt32(index)] = j; break; } } #endif } } //Rooks for (i = 0; i < 64; i++) { int[] squares = new int[64]; int numsquares = 0; UInt64 temp = magicmoves_r_mask[i]; while (temp != 0UL) { int bitCount = BitOps.BitCountWegner(temp); squares[numsquares++] = bitCount; BitOps.BitScanForwardReset(ref temp); //UInt64 bit = temp & -temp; //squares[numsquares++]=initmagicmoves_bitpos64_database[(bit*0x07EDD5E59A4E28C2UL)>>58]; //temp^=bit; } for (temp = 0; temp < (1UL << numsquares); temp++) { UInt64 tempocc = initmagicmoves_occ(squares, numsquares, temp); #if !PERFECT_MAGIC_HASH #if !VARIABLE_SHIFT magicmovesrdb[squares[i], Convert.ToInt32((tempocc * magicmoves_r_magics[squares[i]]) >> 52)] = initmagicmoves_Rmoves(i, tempocc); #else magicmovesrdb[squares[i], Convert.ToInt32((tempocc * magicmoves_r_magics[squares[i]]) >> magicmoves_r_shift[squares[i]])] = initmagicmoves_Rmoves(i, tempocc); #endif #else UInt64 moves = initmagicmoves_Rmoves(i, tempocc); #if !VARIABLE_SHIFT UInt64 index = (((tempocc) * magicmoves_r_magics[i]) >> 52); #else UInt64 index = (((tempocc) * magicmoves_r_magics[i]) >> magicmoves_r_shift[squares[i]]); #endif for (ushort j = 0; j < 4900; j++) { if (~magicmovesrdb[j] != 0UL) { magicmovesrdb[j] = moves; magicmoves_r_indices[i, Convert.ToInt32(index)] = j; break; } else if (magicmovesrdb[j] == moves) { magicmoves_r_indices[i, Convert.ToInt32(index)] = j; break; } } #endif } } }