What is the paradigmatic way to use large global static tables that are initialized once and serve practically as constants in Rust? [duplicate]

蹲街弑〆低调 提交于 2020-05-17 07:47:06

问题


I'm trying to port a Go language chess engine ( https://github.com/easychessanimations/gobbit ) to Rust ( https://github.com/easychessanimations/rustengine ). Problem with Go is that it produces a WASM executable which is bloated in size because it contains the whole Go runtime ( > 2 MB ). Also the native executable could be a bit faster. So I decided to give Rust a try.

Chess engines need a lot of tables that are initialized in the beginning and serve practically as constants throughout the whole lifetime of the program.

Already with initializing attack bitboards I'm having problems.

I define an attack table:

/// AttackTable type records an attack bitboard for every square of a chess board
pub type AttackTable = [Bitboard; BOARD_AREA];

/// EMPTY_ATTACK_TABLE defines an empty attack table, useful for initializing attack tables
pub const EMPTY_ATTACK_TABLE: AttackTable = [
    0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
    0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
];

Then I have global variables of this type:

/// KNIGHT_ATTACK is the attack table of knight
pub static mut KNIGHT_ATTACK: AttackTable = EMPTY_ATTACK_TABLE;
/// BISHOP_ATTACK is the attack table of bishop
pub static mut BISHOP_ATTACK: AttackTable = EMPTY_ATTACK_TABLE;
...

Already at initialization I have to do this in an unsafe block:

/// initializes attack tables, must be called before using the module
pub fn init_attack_tables() {
    let mut sq: Square = 0;
    loop {
        if sq < BOARD_AREA {
            unsafe {
                KNIGHT_ATTACK[sq] = jump_attack_8(sq, KNIGHT_DELTAS, 0);
                BISHOP_ATTACK[sq] = sliding_attack_4(sq, BISHOP_DELTAS, 0);
                ...
            }
            sq += 1;
        } else {
            break;
        }
    }
}

All later accesses to these tables also have to be in unsafe blocks, so I must be doing something wrong.

However I need these tables, they have to be globals and should be accessed easily and quickly. I don't know what to do.

来源:https://stackoverflow.com/questions/61754475/what-is-the-paradigmatic-way-to-use-large-global-static-tables-that-are-initiali

易学教程内所有资源均来自网络或用户发布的内容,如有违反法律规定的内容欢迎反馈
该文章没有解决你所遇到的问题?点击提问,说说你的问题,让更多的人一起探讨吧!