snail.rs

2.1 kB · rust · 55 lines

1use crate::Fault;2use mrlyrs::core::json;3use mrlyrs::num::spiral::{self, Growth, Snail};4use wasm_bindgen::prelude::*;56const TOP: u32 = 2000;7const BASE: u32 = 8;89fn read(base: u32, top: u32, growth: &str) -> Result<Snail, Fault> {10    let growth = growth.parse::<Growth>()?;11    if !(2..=BASE).contains(&base) {12        return Err(Fault::new(format!("the base is 2 to {BASE}.")));13    }14    if top == 0 || top > TOP {15        return Err(Fault::new(format!("the top is 1 to {TOP}.")));16    }17    Ok(spiral::snail(u64::from(base), u64::from(top), growth))18}1920/// Packs the snail of the whole numbers to the top: five numbers a tile, the x and y of its lower-left corner, its side, its level and one when the number is prime, in the order one, two, three and on.21#[wasm_bindgen]22pub fn snail_cells(base: u32, top: u32, growth: &str) -> Result<Vec<i32>, Fault> {23    let shell = read(base, top, growth)?;24    let mut out = Vec::with_capacity(5 * shell.tiles.len());25    for tile in &shell.tiles {26        out.push(tile.x as i32);27        out.push(tile.y as i32);28        out.push(tile.side as i32);29        out.push(tile.level as i32);30        out.push(i32::from(tile.prime));31    }32    Ok(out)33}3435/// Reads the snail: the count of tiles, the primes at or below the top, the tiles grown past a unit cell, the tally at each level, the largest side, the drawn area and the box the tiles fill, as JSON.36#[wasm_bindgen]37pub fn snail_read(base: u32, top: u32, growth: &str) -> Result<String, Fault> {38    let shell = read(base, top, growth)?;39    let grown = shell.tiles.iter().filter(|tile| tile.level > 0).count();40    let side = shell.tiles.iter().map(|tile| tile.side).max().unwrap_or(1);41    Ok(json!({42        "tiles": shell.tiles.len(),43        "primes": shell.primes,44        "grown": grown,45        "levels": shell.levels,46        "peak": shell.levels.len() - 1,47        "side": side,48        "area": shell.area as u64,49        "low": [shell.low.0, shell.low.1],50        "high": [shell.high.0, shell.high.1],51        "width": shell.high.0 - shell.low.0,52        "height": shell.high.1 - shell.low.1,53    })54    .to_string())55}