[board] Refactor ray BitBoard lookups
Rearrange the generated ray bitboards into a 2D grid by square and direction. Use the Direction vector for lookup.
This commit is contained in:
parent
2394afc210
commit
6e483b412b
2 changed files with 47 additions and 76 deletions
|
@ -36,6 +36,10 @@ impl BitBoard {
|
|||
FILES[file]
|
||||
}
|
||||
|
||||
pub fn ray(sq: Square, dir: Direction) -> BitBoard {
|
||||
library().ray(sq, dir)
|
||||
}
|
||||
|
||||
moves_getter!(knight_moves);
|
||||
moves_getter!(bishop_moves);
|
||||
moves_getter!(rook_moves);
|
||||
|
|
|
@ -1,7 +1,7 @@
|
|||
// Eryn Wells <eryn@erynwells.me>
|
||||
|
||||
use super::BitBoard;
|
||||
use crate::Square;
|
||||
use crate::{square::Direction, Square};
|
||||
use std::sync::Once;
|
||||
|
||||
pub(super) const RANKS: [BitBoard; 8] = [
|
||||
|
@ -26,8 +26,9 @@ pub(super) const FILES: [BitBoard; 8] = [
|
|||
BitBoard(0x0101010101010101 << 7),
|
||||
];
|
||||
|
||||
static mut MOVE_LIBRARY: MoveLibrary = MoveLibrary::new();
|
||||
static MOVE_LIBRARY_INIT: Once = Once::new();
|
||||
pub(super) const LIGHT_SQUARES: BitBoard =
|
||||
BitBoard(0x5555 | 0x5555 << 16 | 0x5555 << 32 | 0x5555 << 48);
|
||||
pub(super) const DARK_SQUARES: BitBoard = BitBoard(!LIGHT_SQUARES.0);
|
||||
|
||||
pub(super) fn library() -> &'static MoveLibrary {
|
||||
static MOVE_LIBRARY_INIT: Once = Once::new();
|
||||
|
@ -42,44 +43,6 @@ pub(super) fn library() -> &'static MoveLibrary {
|
|||
}
|
||||
}
|
||||
|
||||
#[derive(Clone, Copy, Debug)]
|
||||
struct OrthogonalRays {
|
||||
positive_rank: BitBoard,
|
||||
positive_file: BitBoard,
|
||||
negative_rank: BitBoard,
|
||||
negative_file: BitBoard,
|
||||
}
|
||||
|
||||
impl OrthogonalRays {
|
||||
const fn new() -> OrthogonalRays {
|
||||
OrthogonalRays {
|
||||
positive_rank: BitBoard::empty(),
|
||||
positive_file: BitBoard::empty(),
|
||||
negative_rank: BitBoard::empty(),
|
||||
negative_file: BitBoard::empty(),
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
#[derive(Clone, Copy, Debug)]
|
||||
struct DiagonalRays {
|
||||
positive_diagonal: BitBoard,
|
||||
positive_antidiagonal: BitBoard,
|
||||
negative_diagonal: BitBoard,
|
||||
negative_antidiagonal: BitBoard,
|
||||
}
|
||||
|
||||
impl DiagonalRays {
|
||||
const fn new() -> DiagonalRays {
|
||||
DiagonalRays {
|
||||
positive_diagonal: BitBoard::empty(),
|
||||
positive_antidiagonal: BitBoard::empty(),
|
||||
negative_diagonal: BitBoard::empty(),
|
||||
negative_antidiagonal: BitBoard::empty(),
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
macro_rules! library_getter {
|
||||
($name:ident) => {
|
||||
pub(super) fn $name(&self, sq: Square) -> BitBoard {
|
||||
|
@ -91,8 +54,7 @@ macro_rules! library_getter {
|
|||
#[derive(Debug)]
|
||||
pub(super) struct MoveLibrary {
|
||||
// Rays
|
||||
diagonal_rays: [DiagonalRays; Square::NUM as usize],
|
||||
orthogonal_rays: [OrthogonalRays; Square::NUM as usize],
|
||||
rays: [[BitBoard; 8]; Square::NUM],
|
||||
|
||||
// Piecewise move tables
|
||||
knight_moves: [BitBoard; 64],
|
||||
|
@ -105,8 +67,7 @@ pub(super) struct MoveLibrary {
|
|||
impl MoveLibrary {
|
||||
const fn new() -> MoveLibrary {
|
||||
MoveLibrary {
|
||||
diagonal_rays: [DiagonalRays::new(); 64],
|
||||
orthogonal_rays: [OrthogonalRays::new(); 64],
|
||||
rays: [[BitBoard::empty(); 8]; Square::NUM],
|
||||
knight_moves: [BitBoard::empty(); 64],
|
||||
bishop_moves: [BitBoard::empty(); 64],
|
||||
rook_moves: [BitBoard::empty(); 64],
|
||||
|
@ -120,31 +81,33 @@ impl MoveLibrary {
|
|||
self.init_orthogonal_rays(sq);
|
||||
self.init_diagonal_rays(sq);
|
||||
self.init_knight_moves(sq as usize);
|
||||
self.init_bishop_moves(sq as usize);
|
||||
self.init_rook_moves(sq as usize);
|
||||
self.init_queen_moves(sq as usize);
|
||||
self.init_bishop_moves(sq);
|
||||
self.init_rook_moves(sq);
|
||||
self.init_queen_moves(sq);
|
||||
self.init_king_moves(sq as usize);
|
||||
}
|
||||
}
|
||||
|
||||
fn init_orthogonal_rays(&mut self, sq: Square) {
|
||||
let sq_bb: BitBoard = sq.into();
|
||||
|
||||
let ortho_rays = &mut self.orthogonal_rays[sq as usize];
|
||||
ortho_rays.positive_file = Self::generate_ray(sq_bb, BitBoard::shift_north_one);
|
||||
ortho_rays.negative_file = Self::generate_ray(sq_bb, BitBoard::shift_south_one);
|
||||
ortho_rays.positive_rank = Self::generate_ray(sq_bb, BitBoard::shift_east_one);
|
||||
ortho_rays.negative_rank = Self::generate_ray(sq_bb, BitBoard::shift_west_one);
|
||||
let rays = &mut self.rays[sq as usize];
|
||||
rays[Direction::North as usize] = Self::generate_ray(sq_bb, BitBoard::shift_north_one);
|
||||
rays[Direction::South as usize] = Self::generate_ray(sq_bb, BitBoard::shift_south_one);
|
||||
rays[Direction::East as usize] = Self::generate_ray(sq_bb, BitBoard::shift_east_one);
|
||||
rays[Direction::West as usize] = Self::generate_ray(sq_bb, BitBoard::shift_west_one);
|
||||
}
|
||||
|
||||
fn init_diagonal_rays(&mut self, sq: Square) {
|
||||
let sq_bb: BitBoard = sq.into();
|
||||
|
||||
let diag_rays = &mut self.diagonal_rays[sq as usize];
|
||||
diag_rays.positive_diagonal = Self::generate_ray(sq_bb, BitBoard::shift_north_east_one);
|
||||
diag_rays.positive_antidiagonal = Self::generate_ray(sq_bb, BitBoard::shift_north_west_one);
|
||||
diag_rays.negative_diagonal = Self::generate_ray(sq_bb, BitBoard::shift_south_west_one);
|
||||
diag_rays.negative_antidiagonal = Self::generate_ray(sq_bb, BitBoard::shift_south_east_one);
|
||||
let rays = &mut self.rays[sq as usize];
|
||||
rays[Direction::NorthEast as usize] =
|
||||
Self::generate_ray(sq_bb, BitBoard::shift_north_east_one);
|
||||
rays[Direction::NorthWest as usize] =
|
||||
Self::generate_ray(sq_bb, BitBoard::shift_north_west_one);
|
||||
rays[Direction::SouthWest as usize] =
|
||||
Self::generate_ray(sq_bb, BitBoard::shift_south_west_one);
|
||||
rays[Direction::SouthEast as usize] =
|
||||
Self::generate_ray(sq_bb, BitBoard::shift_south_east_one);
|
||||
}
|
||||
|
||||
fn init_king_moves(&mut self, idx: usize) {
|
||||
|
@ -179,26 +142,26 @@ impl MoveLibrary {
|
|||
self.knight_moves[idx] = attacks;
|
||||
}
|
||||
|
||||
fn init_bishop_moves(&mut self, idx: usize) {
|
||||
let diag_rays = self.diagonal_rays[idx];
|
||||
self.bishop_moves[idx] = diag_rays.positive_diagonal
|
||||
| diag_rays.negative_diagonal
|
||||
| diag_rays.positive_antidiagonal
|
||||
| diag_rays.negative_antidiagonal;
|
||||
fn init_bishop_moves(&mut self, sq: Square) {
|
||||
let rays = self.rays[sq as usize];
|
||||
self.bishop_moves[sq as usize] = rays[Direction::NorthWest as usize]
|
||||
| rays[Direction::NorthEast as usize]
|
||||
| rays[Direction::SouthEast as usize]
|
||||
| rays[Direction::SouthWest as usize];
|
||||
}
|
||||
|
||||
fn init_rook_moves(&mut self, idx: usize) {
|
||||
let ortho_rays = self.orthogonal_rays[idx];
|
||||
self.rook_moves[idx] = ortho_rays.positive_rank
|
||||
| ortho_rays.negative_rank
|
||||
| ortho_rays.positive_file
|
||||
| ortho_rays.negative_file;
|
||||
fn init_rook_moves(&mut self, sq: Square) {
|
||||
let rays = self.rays[sq as usize];
|
||||
self.rook_moves[sq as usize] = rays[Direction::North as usize]
|
||||
| rays[Direction::East as usize]
|
||||
| rays[Direction::South as usize]
|
||||
| rays[Direction::West as usize];
|
||||
}
|
||||
|
||||
fn init_queen_moves(&mut self, idx: usize) {
|
||||
let rook_moves = self.rook_moves[idx];
|
||||
let bishop_moves = self.bishop_moves[idx];
|
||||
self.queen_moves[idx] = rook_moves | bishop_moves;
|
||||
fn init_queen_moves(&mut self, sq: Square) {
|
||||
let rook_moves = self.rook_moves[sq as usize];
|
||||
let bishop_moves = self.bishop_moves[sq as usize];
|
||||
self.queen_moves[sq as usize] = rook_moves | bishop_moves;
|
||||
}
|
||||
|
||||
#[inline]
|
||||
|
@ -214,6 +177,10 @@ impl MoveLibrary {
|
|||
ray
|
||||
}
|
||||
|
||||
pub(super) fn ray(&self, sq: Square, dir: Direction) -> BitBoard {
|
||||
self.rays[sq as usize][dir as usize]
|
||||
}
|
||||
|
||||
library_getter!(knight_moves);
|
||||
library_getter!(bishop_moves);
|
||||
library_getter!(rook_moves);
|
||||
|
|
Loading…
Add table
Add a link
Reference in a new issue