core_rust/core/game/utils/
actions.rs

1use super::errors::GameError;
2use serde::{Deserialize, Serialize};
3
4/// Available actions in the gridworld.
5///
6/// - Ground moves: Up, Down, Left, Right
7/// - A no-op: `Nothing`
8/// - Abstract actions: `AbstractAction1..8` are used when acting in the abstract MDP.
9///   In a well-formed abstraction, an abstract state typically exposes 2–4 actions.
10/// - `Root` is a sentinel used for the MCTS tree root.
11#[derive(Debug, Clone, Copy, Hash, Eq, PartialEq, Serialize, Deserialize)]
12pub enum Action {
13    Up = 0,
14    Down = 1,
15    Left = 2,
16    Right = 3,
17    Nothing = 4,
18    AbstractAction1 = 5,
19    AbstractAction2 = 6,
20    AbstractAction3 = 7,
21    AbstractAction4 = 8,
22    AbstractAction5 = 9,
23    AbstractAction6 = 10,
24    AbstractAction7 = 11,
25    AbstractAction8 = 12,
26    Root = 13,
27}
28
29impl Action {
30    /// Numeric identifier of this action.
31    pub fn id(&self) -> usize {
32        *self as usize
33    }
34
35    /// Convert a numeric identifier back into an `Action`.
36    pub fn from_id(id: usize) -> Result<Self, GameError> {
37        match id {
38            0 => Ok(Action::Up),
39            1 => Ok(Action::Down),
40            2 => Ok(Action::Left),
41            3 => Ok(Action::Right),
42            4 => Ok(Action::Nothing),
43            5 => Ok(Action::AbstractAction1),
44            6 => Ok(Action::AbstractAction2),
45            7 => Ok(Action::AbstractAction3),
46            8 => Ok(Action::AbstractAction4),
47            9 => Ok(Action::AbstractAction5),
48            10 => Ok(Action::AbstractAction6),
49            11 => Ok(Action::AbstractAction7),
50            12 => Ok(Action::AbstractAction8),
51            value => Err(GameError::InvalidActionId { id: value }),
52        }
53    }
54}