⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 evaluate.cpp

📁 超强国际象棋引擎
💻 CPP
📖 第 1 页 / 共 4 页
字号:

            // penalty

            penalty = (penalty_1 + penalty_2) / 2;
            }

        file = SQUARE_FILE(KING_POS(board, 1));
        penalty += storm_file(board, file, 1);

        if(file != (0x4))
            penalty += storm_file(board, file - 1, 1);

        if(file != (0xB))
            penalty += storm_file(board, file + 1, 1);
        op[me] -= (penalty * 256) / 256;
        }

    // king attacks

    for ( color = 0; color < 2; color++ )
        {
        if((mat_info->cflags[color]&(1 << 3)) != 0)
            {

            me = color;
            opp = COLOUR_OPP(me);

            king = KING_POS(board, me);
            king_file = SQUARE_FILE(king);
            king_rank = SQUARE_RANK(king);

            // piece attacks

            attack_tot = 0;
            piece_nb = 0;

            for ( ptr = &board->piece[opp][1]; (from = *ptr) != 0; ptr++ )
                {

                piece = board->square[from];

                if(piece_attack_king(board, piece, from, king))
                    {
                    piece_nb++;
                    attack_tot += king_attack_unit[piece];
                    }
                }

            // scoring

            op[color] -= (attack_tot * 20 * king_attack_weight[piece_nb]) / 256;
            }
        }

    // update

    *opening += op[0] - op[1];
    *endgame += eg[0] - eg[1];
    }

// eval_passer()

static void eval_passer(const board_t *board, const pawn_info_t *pawn_info, int *opening, int *endgame)
    {

    int color;
    int op[2], eg[2];
    int att, def;
    int bits;
    int file, rank;
    int sq;
    int min, max;
    int delta;
    int white_passed_nb, black_passed_nb;

    // init

    for ( color = 0; color < 2; color++ )
        {
        op[color] = 0;
        eg[color] = 0;
        }

    white_passed_nb = 0;
    black_passed_nb = 0;

    // passed pawns

    for ( color = 0; color < 2; color++ )
        {

        att = color;
        def = COLOUR_OPP(att);

        for ( bits = pawn_info->passed_bits[att]; bits != 0; bits &= bits - 1 )
            {

            file = BIT_FIRST(bits);
            rank = BIT_LAST(board->pawn_file[att][file]);
            sq = SQUARE_MAKE(file, rank);

            if(COLOUR_IS_BLACK(att))
                sq = SQUARE_RANK_MIRROR(sq);

            // opening scoring

            op[att] += quad(10, 70, rank);

            // endgame scoring init

            min = 20;
            max = 140;

            delta = max - min;

            // "dangerous" bonus

            if(board->piece_size[def] <= 1 // defender has no piece
            && (unstoppable_passer(board, sq, att) || king_passer(board, sq, att)))
                {
                delta += 800;
                }
            else if(free_passer(board, sq, att))
                {
                delta += 60;
                }

            // king-distance bonus

            delta -= pawn_att_dist(sq, KING_POS(board, att), att) * 5;
            delta += pawn_def_dist(sq, KING_POS(board, def), att) * 20;

            // endgame scoring

            eg[att] += min;

            if(delta > 0)
                eg[att] += quad(0, delta, rank);
            }
        }

    // update

    *opening += op[0] - op[1];
    *endgame += eg[0] - eg[1];
    }

// eval_pattern()

static void eval_pattern(const board_t *board, int *opening, int *endgame)
    {

    // trapped bishop (7th rank)

    if((board->square[(0xA4)] == ((1 << 5) | (1 << 0)) && board->square[(0x95)] == ((1 << 3) | (1 << 1)))
        || (board->square[(0xB5)] == ((1 << 5) | (1 << 0)) && board->square[(0xA6)] == ((1 << 3) | (1 << 1))))
        {
        *opening -= 100;
        *endgame -= 100;
        }

    if((board->square[(0xAB)] == ((1 << 5) | (1 << 0)) && board->square[(0x9A)] == ((1 << 3) | (1 << 1)))
        || (board->square[(0xBA)] == ((1 << 5) | (1 << 0)) && board->square[(0xA9)] == ((1 << 3) | (1 << 1))))
        {
        *opening -= 100;
        *endgame -= 100;
        }

    if((board->square[(0x54)] == ((1 << 5) | (1 << 1)) && board->square[(0x65)] == ((1 << 2) | (1 << 0)))
        || (board->square[(0x45)] == ((1 << 5) | (1 << 1)) && board->square[(0x56)] == ((1 << 2) | (1 << 0))))
        {
        *opening += 100;
        *endgame += 100;
        }

    if((board->square[(0x5B)] == ((1 << 5) | (1 << 1)) && board->square[(0x6A)] == ((1 << 2) | (1 << 0)))
        || (board->square[(0x4A)] == ((1 << 5) | (1 << 1)) && board->square[(0x59)] == ((1 << 2) | (1 << 0))))
        {
        *opening += 100;
        *endgame += 100;
        }

    // trapped bishop (6th rank)

    if(board->square[(0x94)] == ((1 << 5) | (1 << 0)) && board->square[(0x85)] == ((1 << 3) | (1 << 1)))
        {
        *opening -= 100 / 2;
        *endgame -= 100 / 2;
        }

    if(board->square[(0x9B)] == ((1 << 5) | (1 << 0)) && board->square[(0x8A)] == ((1 << 3) | (1 << 1)))
        {
        *opening -= 100 / 2;
        *endgame -= 100 / 2;
        }

    if(board->square[(0x64)] == ((1 << 5) | (1 << 1)) && board->square[(0x75)] == ((1 << 2) | (1 << 0)))
        {
        *opening += 100 / 2;
        *endgame += 100 / 2;
        }

    if(board->square[(0x6B)] == ((1 << 5) | (1 << 1)) && board->square[(0x7A)] == ((1 << 2) | (1 << 0)))
        {
        *opening += 100 / 2;
        *endgame += 100 / 2;
        }

    // blocked bishop

    if(board->square[(0x57)] == ((1 << 2) | (1 << 0)) && board->square[(0x67)] != 0
        && board->square[(0x46)] == ((1 << 5) | (1 << 0)))
        {
        *opening -= 50;
        }

    if(board->square[(0x58)] == ((1 << 2) | (1 << 0)) && board->square[(0x68)] != 0
        && board->square[(0x49)] == ((1 << 5) | (1 << 0)))
        {
        *opening -= 50;
        }

    if(board->square[(0xA7)] == ((1 << 3) | (1 << 1)) && board->square[(0x97)] != 0
        && board->square[(0xB6)] == ((1 << 5) | (1 << 1)))
        {
        *opening += 50;
        }

    if(board->square[(0xA8)] == ((1 << 3) | (1 << 1)) && board->square[(0x98)] != 0
        && board->square[(0xB9)] == ((1 << 5) | (1 << 1)))
        {
        *opening += 50;
        }

    // blocked rook

    if((board->square[(0x46)] == ((1 << 7) | (1 << 0)) || board->square[(0x45)] == ((1 << 7) | (1 << 0)))
        && (board->square[(0x44)] == ((1 << 6) | (1 << 0)) || board->square[(0x54)] == ((1 << 6) | (1 << 0))
            || board->square[(0x45)] == ((1 << 6) | (1 << 0))))
        {
        *opening -= 50;
        }

    if((board->square[(0x49)] == ((1 << 7) | (1 << 0)) || board->square[(0x4A)] == ((1 << 7) | (1 << 0)))
        && (board->square[(0x4B)] == ((1 << 6) | (1 << 0)) || board->square[(0x5B)] == ((1 << 6) | (1 << 0))
            || board->square[(0x4A)] == ((1 << 6) | (1 << 0))))
        {
        *opening -= 50;
        }

    if((board->square[(0xB6)] == ((1 << 7) | (1 << 1)) || board->square[(0xB5)] == ((1 << 7) | (1 << 1)))
        && (board->square[(0xB4)] == ((1 << 6) | (1 << 1)) || board->square[(0xA4)] == ((1 << 6) | (1 << 1))
            || board->square[(0xB5)] == ((1 << 6) | (1 << 1))))
        {
        *opening += 50;
        }

    if((board->square[(0xB9)] == ((1 << 7) | (1 << 1)) || board->square[(0xBA)] == ((1 << 7) | (1 << 1)))
        && (board->square[(0xBB)] == ((1 << 6) | (1 << 1)) || board->square[(0xAB)] == ((1 << 6) | (1 << 1))
            || board->square[(0xBA)] == ((1 << 6) | (1 << 1))))
        {
        *opening += 50;
        }
    }

// unstoppable_passer()

static bool unstoppable_passer(const board_t *board, int pawn, int color)
    {

    int me, opp;
    int file, rank;
    int king;
    int prom;
    const sq_t *ptr;
    int sq;
    int dist;

    me = color;
    opp = COLOUR_OPP(me);

    file = SQUARE_FILE(pawn);
    rank = PAWN_RANK(pawn, me);

    king = KING_POS(board, opp);

    // clear promotion path?

    for ( ptr = &board->piece[me][0]; (sq = *ptr) != 0; ptr++ )
        {
        if(SQUARE_FILE(sq) == file && PAWN_RANK(sq, me) > rank)
            {
            return false; // "friendly" blocker
            }
        }

    // init

    if(rank == (0x5))
        {
        pawn += PAWN_MOVE_INC(me);
        rank++;
        }

    prom = PAWN_PROMOTE(pawn, me);

    dist = DISTANCE(pawn, prom);

    if(board->turn == opp)
        dist++;

    if(DISTANCE(king, prom) > dist)
        return true; // not in the square

    return false;
    }

// king_passer()

static bool king_passer(const board_t *board, int pawn, int color)
    {

    int me;
    int king;
    int file;
    int prom;

    me = color;

    king = KING_POS(board, me);
    file = SQUARE_FILE(pawn);
    prom = PAWN_PROMOTE(pawn, me);

    if(DISTANCE(king, prom) <= 1 && DISTANCE(king, pawn) <= 1
        && (SQUARE_FILE(king) != file || (file != (0x4) && file != (0xB))))
        {
        return true;
        }

    return false;
    }

// free_passer()

static bool free_passer(const board_t *board, int pawn, int color)
    {

    int me, opp;
    int inc;
    int sq;
    int move;

    me = color;
    opp = COLOUR_OPP(me);

    inc = PAWN_MOVE_INC(me);
    sq = pawn + inc;

    if(board->square[sq] != 0)
        return false;

    move = MOVE_MAKE(pawn, sq);

    if(see_move(move, board) < 0)
        return false;

    return true;
    }

// pawn_att_dist()

static int pawn_att_dist(int pawn, int king, int color)
    {

    int me;
    int inc;
    int target;

    me = color;
    inc = PAWN_MOVE_INC(me);

    target = pawn + inc;

    return DISTANCE(king, target);
    }

// pawn_def_dist()

static int pawn_def_dist(int pawn, int king, int color)
    {

    int me;
    int inc;
    int target;

    me = color;
    inc = PAWN_MOVE_INC(me);

    target = pawn + inc;

    return DISTANCE(king, target);
    }

// draw_init_list()

static void draw_init_list(int list [], const board_t *board, int pawn_colour)
    {

    int pos;
    int att, def;
    const sq_t *ptr;
    int sq;
    int pawn;
    int i;

    // init

    pos = 0;

    att = pawn_colour;
    def = COLOUR_OPP(att);

    // att

    for ( ptr = &board->piece[att][0]; (sq = *ptr) != 0; ptr++ )
        {
        list[pos++] = sq;
        }

    for ( ptr = &board->pawn[att][0]; (sq = *ptr) != 0; ptr++ )
        {
        list[pos++] = sq;
        }

    // def

    for ( ptr = &board->piece[def][0]; (sq = *ptr) != 0; ptr++ )
        {
        list[pos++] = sq;
        }

    for ( ptr = &board->pawn[def][0]; (sq = *ptr) != 0; ptr++ )
        {
        list[pos++] = sq;
        }

    // end marker

    list[pos] = 0;

    // file flip?

    pawn = board->pawn[att][0];

    if(SQUARE_FILE(pawn) >= (0x8))
        {
        for ( i = 0; i < pos; i++ )
            {
            list[i] = SQUARE_FILE_MIRROR(list[i]);
            }
        }

    // rank flip?

    if(COLOUR_IS_BLACK(pawn_colour))
        {
        for ( i = 0; i < pos; i++ )
            {
            list[i] = SQUARE_RANK_MIRROR(list[i]);
            }
        }
    }

// draw_kpkq()

static bool draw_kpkq(const int list [], int turn)
    {

    int wk, wp, bk, bq;
    int prom;
    int dist;

    // load

    wk = *list++;

    wp = *list++;

    bk = *list++;

    bq = *list++;

    // test

    if(false) { }
    else if(wp == (0xA4))
        {

        prom = (0xB4);

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -