brutus tweaks
parent
00270569db
commit
786e70fe9a
|
@ -2,6 +2,7 @@ use std::{cmp::Ordering, iter};
|
|||
|
||||
use anyhow::Result;
|
||||
use itertools::Itertools;
|
||||
use rand::{seq::SliceRandom, thread_rng};
|
||||
use rayon::iter::{ParallelBridge, ParallelIterator};
|
||||
|
||||
use super::{Agent, Chase, MaximizerAgent, MinimizerAgent};
|
||||
|
@ -27,14 +28,20 @@ impl Brutus {
|
|||
.collect_vec();
|
||||
|
||||
if symbols.is_empty() {
|
||||
return Chase::new(self.player).step_max(board);
|
||||
return if minimize {
|
||||
Chase::new(self.player).step_min(board)
|
||||
} else {
|
||||
Chase::new(self.player).step_max(board)
|
||||
};
|
||||
}
|
||||
|
||||
// Number of free slots
|
||||
let n_free = board.get_board().iter().filter(|x| x.is_none()).count();
|
||||
|
||||
// Number of slots we need to fill with numbers
|
||||
let n_fill = n_free - symbols.len();
|
||||
// Add one if we have two or fewer symbols available, so that we can
|
||||
// account for one unused symbol while keeping a reasonable runtime
|
||||
let n_fill = n_free - symbols.len() + if symbols.len() <= 2 { 1 } else { 0 };
|
||||
|
||||
let mut items = iter::repeat(None)
|
||||
.take(n_fill)
|
||||
|
@ -70,7 +77,7 @@ impl Brutus {
|
|||
.collect::<Vec<_>>();
|
||||
|
||||
if minimize {
|
||||
// Sort from smallest midpoint to biggest midpoint
|
||||
// Sort from smallest to biggest midpoint
|
||||
items.sort_by(|a, b| a.1.partial_cmp(&b.1).unwrap_or(Ordering::Equal));
|
||||
} else {
|
||||
items.sort_by(|a, b| b.1.partial_cmp(&a.1).unwrap_or(Ordering::Equal));
|
||||
|
@ -88,15 +95,27 @@ impl Brutus {
|
|||
|
||||
let (t, _) = items.first().unwrap();
|
||||
|
||||
for (i, s) in t.get_board().iter().enumerate() {
|
||||
if let Some(s) = s {
|
||||
if s.is_op() && board.get_board()[i].is_none() {
|
||||
return Ok(PlayerAction { pos: i, symb: *s });
|
||||
let mut symbols = symbols.clone();
|
||||
symbols.shuffle(&mut thread_rng());
|
||||
|
||||
// Place a random unused symbol
|
||||
for target_s in symbols {
|
||||
for (i, s) in t.get_board().iter().enumerate() {
|
||||
if let Some(s) = s {
|
||||
if board.get_board()[i].is_none() && target_s == *s {
|
||||
return Ok(PlayerAction { pos: i, symb: *s });
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
unreachable!()
|
||||
// Final escape hatch, if we didn't decide to place any symbols
|
||||
// (which is possible, since we add one to free_spots above!)
|
||||
if minimize {
|
||||
Chase::new(self.player).step_min(board)
|
||||
} else {
|
||||
Chase::new(self.player).step_max(board)
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
|
|
Loading…
Reference in New Issue