use std::io::Result;
use std::io::Write;
use std::mem::transmute;
use super::types::{BitBoard, File, Rank, Square};
pub fn squares_between(start: Square, end: Square) -> BitBoard {
if start == end {
return BitBoard::EMPTY;
}
let mut bitboard: BitBoard = BitBoard::EMPTY;
let (start_rank, start_file) = (start.rank() as i8, start.file() as i8);
let (end_rank, end_file) = (end.rank() as i8, end.file() as i8);
let (dr, df) = match (end_rank - start_rank, end_file - start_file) {
(0, df) if df != 0 => (0, df.signum()),
(dr, 0) if dr != 0 => (dr.signum(), 0),
(dr, df) if dr.abs() == df.abs() => (dr.signum(), df.signum()),
_ => return BitBoard::EMPTY,
};
let mut new_rank: i8 = start_rank + dr;
let mut new_file: i8 = start_file + df;
while (new_rank, new_file) != (end_rank, end_file) {
if (0..8).contains(&new_rank) && (0..8).contains(&new_file) {
let square: Square =
Square::from_file_rank(unsafe { transmute::<u8, File>(new_file as u8) }, unsafe {
transmute::<u8, Rank>(new_rank as u8)
});
bitboard = bitboard.set_square(square);
} else {
break;
}
new_rank += dr;
new_file += df;
}
bitboard = bitboard.set_square(end);
bitboard
}
pub fn gen_between() -> [[BitBoard; Square::NUM_SQUARES]; Square::NUM_SQUARES] {
let mut table: [[BitBoard; Square::NUM_SQUARES]; Square::NUM_SQUARES] =
[[BitBoard::EMPTY; Square::NUM_SQUARES]; Square::NUM_SQUARES];
for start in BitBoard::FULL {
for end in BitBoard::FULL {
table[start.to_index()][end.to_index()] = squares_between(start, end);
}
}
table
}
pub fn write_between(
name: &str,
table: &[[BitBoard; Square::NUM_SQUARES]; Square::NUM_SQUARES],
out: &mut impl Write,
) -> Result<()> {
writeln!(
out,
"static {}_ARRAY: [[u64; {}]; {}] = [",
name,
Square::NUM_SQUARES,
Square::NUM_SQUARES
)?;
for row in table {
write!(out, " [")?;
for entry in row {
write!(out, "{}, ", entry.0)?;
}
writeln!(out, "],")?;
}
writeln!(out, "];")?;
Ok(())
}