diff --git a/battlesnake/Cargo.toml b/battlesnake/Cargo.toml index fe0daa0..734fdb0 100644 --- a/battlesnake/Cargo.toml +++ b/battlesnake/Cargo.toml @@ -19,7 +19,7 @@ nursery = "warn" # server tokio = { version = "1.43", features = ["net", "macros", "rt-multi-thread"] } axum = { version = "0.8", features = ["http2", "multipart", "ws"] } -serde = { version = "1.0", features = ["derive"] } +serde = { version = "1.0", features = ["derive", "rc"] } # logging log = "0.4" diff --git a/battlesnake/benches/simulation.rs b/battlesnake/benches/simulation.rs index 5316314..1b5c2d4 100644 --- a/battlesnake/benches/simulation.rs +++ b/battlesnake/benches/simulation.rs @@ -1,4 +1,7 @@ -use std::sync::atomic::{AtomicU32, Ordering}; +use std::sync::{ + atomic::{AtomicU32, Ordering}, + Arc, +}; use criterion::{black_box, criterion_group, criterion_main, Bencher, BenchmarkId, Criterion}; @@ -9,7 +12,7 @@ use battlesnake::types::{ }; fn create_start_snake(coord: Coord) -> Battlesnake { - let id = format!("{coord:?}"); + let id: Arc = format!("{coord:?}").into(); Battlesnake { id: id.clone(), name: id.clone(), @@ -18,7 +21,7 @@ fn create_start_snake(coord: Coord) -> Battlesnake { latency: "0".into(), head: coord, length: 3, - shout: String::new(), + shout: None, squad: id, } } diff --git a/battlesnake/src/types/simulation.rs b/battlesnake/src/types/simulation.rs index df53c79..d2d8397 100644 --- a/battlesnake/src/types/simulation.rs +++ b/battlesnake/src/types/simulation.rs @@ -3,6 +3,7 @@ use std::{ fmt::Display, num::NonZeroUsize, ops::{Deref, DerefMut}, + sync::Arc, }; use bitvec::prelude::*; @@ -70,6 +71,7 @@ pub struct Board { free: SmallBitBox, snakes: Vec, constrictor: bool, + id_map: Arc<[(u8, Arc)]>, } impl From<&Request> for Board { @@ -77,6 +79,18 @@ impl From<&Request> for Board { let width = value.board.width; let height = value.board.height; let fields = usize::from(width) * usize::from(height); + let id_map = value + .board + .snakes + .iter() + .enumerate() + .filter_map(|(i, snake)| { + u8::try_from(i) + .inspect_err(|e| warn!("unable to convert id to u8: {e}")) + .ok() + .map(|i| (i, snake.id.clone())) + }) + .collect::>(); let mut board = Self { width, height, @@ -88,7 +102,8 @@ impl From<&Request> for Board { hazard: SmallBitBox::new(false, fields), free: SmallBitBox::new(true, fields), snakes: Vec::with_capacity(value.board.snakes.len()), - constrictor: value.game.ruleset.name == "constrictor", + constrictor: &*value.game.ruleset.name == "constrictor", + id_map: id_map.into(), }; for &food in &value.board.food { diff --git a/battlesnake/src/types/wire.rs b/battlesnake/src/types/wire.rs index 214686b..7fe22c5 100644 --- a/battlesnake/src/types/wire.rs +++ b/battlesnake/src/types/wire.rs @@ -1,3 +1,5 @@ +use std::sync::Arc; + use serde::{Deserialize, Serialize}; use super::{Coord, Direction}; @@ -17,11 +19,11 @@ pub struct Request { #[derive(Debug, PartialEq, Eq, Clone, Deserialize)] pub struct Game { /// A unique identifier for this Game. - pub id: String, + pub id: Arc, /// Information about the ruleset being used to run this Game. pub ruleset: Ruleset, /// The name of the map being played on. - pub map: String, + pub map: Arc, /// How much time your snake has to respond to requests for this Game. pub timeout: u16, /// The source of this Game. @@ -31,15 +33,15 @@ pub struct Game { /// - arena /// - challenge /// - custom - pub source: String, + pub source: Arc, } #[derive(Debug, PartialEq, Eq, Clone, Deserialize)] pub struct Ruleset { /// Name of the ruleset being used to run this game. - pub name: String, + pub name: Arc, /// The release version of the Rules module used in this game. - pub version: String, + pub version: Arc, /// A collection of specific settings being used by the current game that control how the rules /// are applied. pub settings: Settings, @@ -84,9 +86,9 @@ pub struct Board { #[derive(Debug, PartialEq, Eq, Clone, Deserialize)] pub struct Battlesnake { /// Unique identifier for this Battlesnake in the context of the current Game. - pub id: String, + pub id: Arc, /// Name given to this Battlesnake by its author - pub name: String, + pub name: Arc, /// Health value of this Battlesnake, between 0 and 100 pub health: u8, /// Array of coordinates representing the Battlesnake's location on the game board. @@ -94,7 +96,7 @@ pub struct Battlesnake { pub body: Vec, /// The previous response time of this Battlesnake, in milliseconds. /// If the Battlesnake timed out and failed to respond, the game timeout will be returned - pub latency: String, + pub latency: Arc, /// Coordinates for this Battlesnake's head. /// Equivalent to the first element of the body array. pub head: Coord, @@ -102,10 +104,10 @@ pub struct Battlesnake { /// Equivalent to the length of the body array. pub length: u16, /// Message shouted by this Battlesnake on the previous turn - pub shout: String, + pub shout: Option>, /// The squad that the Battlesnake belongs to. /// Used to identify squad members in Squad Mode games. - pub squad: String, + pub squad: Arc, } #[derive(Debug, PartialEq, Eq, Clone, Serialize)]