Skip to content

Commit 4135443

Browse files
committed
feat: expose more nim utils
1 parent 337211e commit 4135443

File tree

2 files changed

+27
-4
lines changed

2 files changed

+27
-4
lines changed

crates/game-solver/src/player.rs

Lines changed: 3 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -77,7 +77,9 @@ impl TwoPlayer for PartizanPlayer {}
7777

7878
/// Represents a player in a zero-sum (2-player) game,
7979
/// where the game is impartial. That is,
80-
/// the only difference between players is who goes first.
80+
/// the only difference between players is who goes first,
81+
/// and the only thing that defines a game is its 'state':
82+
/// both players need to have the same winning criteria for this player to be used.
8183
#[derive(PartialEq, Eq, Debug, Clone, Copy, Hash)]
8284
pub enum ImpartialPlayer {
8385
/// The player that will play on the current game state,

crates/nimnim/src/lib.rs

Lines changed: 24 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -1,7 +1,12 @@
1-
use std::ops::Add;
1+
use std::{collections::HashSet, ops::Add};
22

3-
#[derive(PartialEq, PartialOrd, Eq, Ord, Debug)]
4-
struct Nimber(usize);
3+
/// A nimber is the size of a heap in a single-stack nim game.
4+
///
5+
/// Nim is crucial for loop-free* impartial combinatorial game theory analysis.
6+
///
7+
/// *This structure does not define utilities for loopy nimbers.
8+
#[derive(Copy, Clone, PartialEq, PartialOrd, Eq, Ord, Debug, Hash)]
9+
pub struct Nimber(pub usize);
510

611
impl Add for Nimber {
712
type Output = Nimber;
@@ -13,6 +18,22 @@ impl Add for Nimber {
1318
}
1419
}
1520

21+
/// Returns Some(minimum excluded value of `list`), or `None` iff `list.is_empty()`
22+
pub fn mex(list: &[Nimber]) -> Option<Nimber> {
23+
let mut mex: Option<Nimber> = None;
24+
let mut set: HashSet<Nimber> = HashSet::with_capacity(list.len());
25+
26+
for item in list {
27+
if set.insert(*item) {
28+
if item > &mex.unwrap_or(Nimber(0)) {
29+
mex = Some(*item)
30+
}
31+
}
32+
}
33+
34+
mex
35+
}
36+
1637
#[cfg(test)]
1738
mod tests {
1839
use crate::Nimber;

0 commit comments

Comments
 (0)