Skip to content

Commit

Permalink
refactor: move reversi file to separate module
Browse files Browse the repository at this point in the history
  • Loading branch information
LeoDog896 committed May 28, 2024
1 parent d96afda commit 9cdda7f
Show file tree
Hide file tree
Showing 5 changed files with 88 additions and 76 deletions.
11 changes: 10 additions & 1 deletion crates/games/src/nim/cli.rs
Original file line number Diff line number Diff line change
@@ -1,9 +1,18 @@
use std::env::args;
use std::{env::args, fmt::{Display, Formatter}};

use game_solver::{game::Game, par_move_scores};

use crate::nim::Nim;

impl Display for Nim {
fn fmt(&self, f: &mut Formatter) -> Result<(), std::fmt::Error> {
for (i, &heap) in self.heaps.iter().enumerate() {
writeln!(f, "Heap {}: {}", i, heap)?;
}
Ok(())
}
}

pub fn main() {
// parse the original configuration of the game from args
// e.g. 3,5,7 for 3 heaps with 3, 5, and 7 objects respectively
Expand Down
14 changes: 1 addition & 13 deletions crates/games/src/nim/mod.rs
Original file line number Diff line number Diff line change
Expand Up @@ -8,10 +8,7 @@
pub mod cli;

use game_solver::game::{Game, ZeroSumPlayer};
use std::{
fmt::{Display, Formatter},
hash::Hash,
};
use std::hash::Hash;

#[derive(Clone, Hash, Eq, PartialEq)]
struct Nim {
Expand Down Expand Up @@ -105,12 +102,3 @@ impl Game for Nim {
false
}
}

impl Display for Nim {
fn fmt(&self, f: &mut Formatter) -> Result<(), std::fmt::Error> {
for (i, &heap) in self.heaps.iter().enumerate() {
writeln!(f, "Heap {}: {}", i, heap)?;
}
Ok(())
}
}
55 changes: 28 additions & 27 deletions crates/games/src/reversi/cli.rs
Original file line number Diff line number Diff line change
@@ -1,9 +1,10 @@
use std::str::FromStr;
use std::fmt;

use clap::Args;
use itertools::Itertools;
use crate::reversi::{Reversi, ReversiMove};
use game_solver::{game::Game, par_move_scores};
use game_solver::{game::{Game, ZeroSumPlayer}, par_move_scores};

use super::{HEIGHT, WIDTH};

#[derive(Args)]
pub struct ReversiArgs {
Expand All @@ -12,34 +13,34 @@ pub struct ReversiArgs {
moves: Vec<ReversiMove>
}

impl FromStr for ReversiMove {
type Err = String;
fn player_to_char(player: Option<ZeroSumPlayer>) -> char {
match player {
Some(ZeroSumPlayer::One) => 'X',
Some(ZeroSumPlayer::Two) => 'O',
None => '-',
}
}

fn from_str(s: &str) -> Result<Self, Self::Err> {
let numbers = s.split("-").collect::<Vec<_>>();
impl fmt::Display for Reversi {
fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
writeln!(f, "Current player: {}", player_to_char(Some(self.player())))?;

if numbers.len() != 2 {
return Err("Must be two numbers separated by a hyphen (x-y), i.e. 2-6".to_string());
}
let moves = self.possible_moves().collect::<Vec<_>>();

let numbers = numbers.iter()
.map(|num| num.parse::<usize>())
.collect::<Vec<_>>();
for y in 0..HEIGHT {
for x in 0..WIDTH {
let character = if moves.contains(&ReversiMove((x, y))) {
'*'
} else {
player_to_char(*self.board.get(x, y).unwrap())
};

if let Some((position, _)) = numbers.iter().find_position(|x| x.is_err()) {
let position = if position == 0 {
"first"
} else {
"second"
};

return Err(format!("The {} number is not a number.", position));
write!(f, "{}", character)?;
}
writeln!(f)?;
}

Ok(ReversiMove((
numbers[0].clone().unwrap(),
numbers[1].clone().unwrap()
)))

Ok(())
}
}

Expand Down Expand Up @@ -75,7 +76,7 @@ pub fn main(args: ReversiArgs) {
println!("\n\nBest moves @ score {}:", score);
current_move_score = Some(score);
}
print!("{:?}, ", game_move);
print!("{}, ", game_move);
}
println!();
}
Expand Down
39 changes: 4 additions & 35 deletions crates/games/src/reversi/mod.rs
Original file line number Diff line number Diff line change
Expand Up @@ -3,11 +3,14 @@
//!
//! More information: <https://en.wikipedia.org/wiki/Reversi>
pub mod mv;
pub mod cli;

use array2d::Array2D;
use game_solver::game::{Game, ZeroSumPlayer};
use std::{fmt, hash::Hash};
use std::hash::Hash;

use self::mv::ReversiMove;

pub const WIDTH: usize = 6;
pub const HEIGHT: usize = 6;
Expand Down Expand Up @@ -139,9 +142,6 @@ impl Reversi {
}
}

#[derive(Clone, Debug, Copy, PartialEq)]
pub struct ReversiMove((usize, usize));

impl Game for Reversi {
type Move = ReversiMove;
type Iter<'a> = std::vec::IntoIter<Self::Move>;
Expand Down Expand Up @@ -207,34 +207,3 @@ impl Game for Reversi {
self.winning_player().is_none() && self.possible_moves().next().is_none()
}
}

fn player_to_char(player: Option<ZeroSumPlayer>) -> char {
match player {
Some(ZeroSumPlayer::One) => 'X',
Some(ZeroSumPlayer::Two) => 'O',
None => '-',
}
}

impl fmt::Display for Reversi {
fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
writeln!(f, "Current player: {}", player_to_char(Some(self.player())))?;

let moves = self.possible_moves().collect::<Vec<_>>();

for y in 0..HEIGHT {
for x in 0..WIDTH {
let character = if moves.contains(&ReversiMove((x, y))) {
'*'
} else {
player_to_char(*self.board.get(x, y).unwrap())
};

write!(f, "{}", character)?;
}
writeln!(f)?;
}

Ok(())
}
}
45 changes: 45 additions & 0 deletions crates/games/src/reversi/mv.rs
Original file line number Diff line number Diff line change
@@ -0,0 +1,45 @@
// TODO: make generic as some n-tuple move (macro generation / dynamic type?)

use std::{fmt::Display, str::FromStr};

use itertools::Itertools;

#[derive(Clone, Debug, Copy, PartialEq)]
pub struct ReversiMove(pub (usize, usize));

impl FromStr for ReversiMove {
type Err = String;

fn from_str(s: &str) -> Result<Self, Self::Err> {
let numbers = s.split("-").collect::<Vec<_>>();

if numbers.len() != 2 {
return Err("Must be two numbers separated by a hyphen (x-y), i.e. 2-6".to_string());
}

let numbers = numbers.iter()
.map(|num| num.parse::<usize>())
.collect::<Vec<_>>();

if let Some((position, _)) = numbers.iter().find_position(|x| x.is_err()) {
let position = if position == 0 {
"first"
} else {
"second"
};

return Err(format!("The {} number is not a number.", position));
}

Ok(ReversiMove((
numbers[0].clone().unwrap(),
numbers[1].clone().unwrap()
)))
}
}

impl Display for ReversiMove {
fn fmt(&self, f: &mut std::fmt::Formatter<'_>) -> std::fmt::Result {
write!(f, "{}-{}", self.0.0, self.0.1)
}
}

0 comments on commit 9cdda7f

Please sign in to comment.