Skip to content

Commit

Permalink
Add problem 1958: Check if Move is Legal
Browse files Browse the repository at this point in the history
  • Loading branch information
EFanZh committed Dec 13, 2023
1 parent ab85b8b commit e35217d
Show file tree
Hide file tree
Showing 3 changed files with 127 additions and 0 deletions.
1 change: 1 addition & 0 deletions src/lib.rs
Original file line number Diff line number Diff line change
Expand Up @@ -1369,6 +1369,7 @@ pub mod problem_1944_number_of_visible_people_in_a_queue;
pub mod problem_1945_sum_of_digits_of_string_after_convert;
pub mod problem_1952_three_divisors;
pub mod problem_1957_delete_characters_to_make_fancy_string;
pub mod problem_1958_check_if_move_is_legal;
pub mod problem_1961_check_if_string_is_a_prefix_of_array;
pub mod problem_1962_remove_stones_to_minimize_the_total;
pub mod problem_1963_minimum_number_of_swaps_to_make_the_string_balanced;
Expand Down
77 changes: 77 additions & 0 deletions src/problem_1958_check_if_move_is_legal/iterative.rs
Original file line number Diff line number Diff line change
@@ -0,0 +1,77 @@
pub struct Solution;

// ------------------------------------------------------ snip ------------------------------------------------------ //

use std::iter;

impl Solution {
fn is_legal(board: &[u8; 64], mut location: (u8, u8), step: (u8, u8), middle: u8, end: u8) -> bool {
location = (location.0.wrapping_add(step.0), location.1.wrapping_add(step.1));

let mut iter = iter::from_fn(|| {
(location.0 < 8 && location.1 < 8).then(|| {
let result = board[usize::from(location.0 * 8 + location.1)];

location = (location.0.wrapping_add(step.0), location.1.wrapping_add(step.1));

result
})
});

if iter.next() == Some(middle) {
for value in iter {
if value == end {
return true;
} else if value != middle {
break;
}
}
}

false
}

pub fn check_move(board: Vec<Vec<char>>, r_move: i32, c_move: i32, color: char) -> bool {
let mut board_2 = [0_u8; 64];

for (target, cell) in board_2.iter_mut().zip(board.into_iter().flatten()) {
*target = cell as _;
}

let location = (r_move as _, c_move as _);
let (middle, end) = if color == 'B' { (b'W', b'B') } else { (b'B', b'W') };

for step in [
(u8::MAX, u8::MAX),
(u8::MAX, 0),
(u8::MAX, 1),
(0, u8::MAX),
(0, 1),
(1, u8::MAX),
(1, 0),
(1, 1),
] {
if Self::is_legal(&board_2, location, step, middle, end) {
return true;
}
}

false
}
}

// ------------------------------------------------------ snip ------------------------------------------------------ //

impl super::Solution for Solution {
fn check_move(board: Vec<Vec<char>>, r_move: i32, c_move: i32, color: char) -> bool {
Self::check_move(board, r_move, c_move, color)
}
}

#[cfg(test)]
mod tests {
#[test]
fn test_solution() {
super::super::tests::run::<super::Solution>();
}
}
49 changes: 49 additions & 0 deletions src/problem_1958_check_if_move_is_legal/mod.rs
Original file line number Diff line number Diff line change
@@ -0,0 +1,49 @@
pub mod iterative;

pub trait Solution {
fn check_move(board: Vec<Vec<char>>, r_move: i32, c_move: i32, color: char) -> bool;
}

#[cfg(test)]
mod tests {
use super::Solution;

pub fn run<S: Solution>() {
let test_cases = [
(
(
[
"...B....", "...W....", "...W....", "...W....", "WBB.WWWB", "...B....", "...B....", "...W....",
],
4,
3,
'B',
),
true,
),
(
(
[
"........", ".B..W...", "..W.....", "...WB...", "........", "....BW..", "......W.", ".......B",
],
4,
4,
'W',
),
false,
),
];

for ((board, r_move, c_move, color), expected) in test_cases {
assert_eq!(
S::check_move(
board.iter().map(|row| row.chars().collect()).collect(),
r_move,
c_move,
color,
),
expected,
);
}
}
}

0 comments on commit e35217d

Please sign in to comment.