Update tools
This commit is contained in:
parent
be00b21905
commit
b0b1a4ce43
@ -4,6 +4,7 @@ use bevy::tasks::ParallelSlice;
|
|||||||
use crate::system::spaces::square_grid::{Grid2D, Grid3D};
|
use crate::system::spaces::square_grid::{Grid2D, Grid3D};
|
||||||
use itertools::{Itertools, MinMaxResult};
|
use itertools::{Itertools, MinMaxResult};
|
||||||
use clap::Parser;
|
use clap::Parser;
|
||||||
|
use serde::Serialize;
|
||||||
use crate::BoxCountCli;
|
use crate::BoxCountCli;
|
||||||
use crate::cli::cli::OutputFormat;
|
use crate::cli::cli::OutputFormat;
|
||||||
use crate::system::{GriddedPosition, Position};
|
use crate::system::{GriddedPosition, Position};
|
||||||
@ -15,30 +16,30 @@ fn bb(data: &Vec<Grid2D>) -> ((i32, i32), (i32, i32)) {
|
|||||||
.iter().minmax_by(|a, b| a.x.cmp(&b.x));
|
.iter().minmax_by(|a, b| a.x.cmp(&b.x));
|
||||||
|
|
||||||
let y = data
|
let y = data
|
||||||
.iter().minmax_by(|a, b| a.x.cmp(&b.x));
|
.iter().minmax_by(|a, b| a.y.cmp(&b.y));
|
||||||
|
|
||||||
match (x, y) {
|
match (x, y) {
|
||||||
(MinMaxResult::MinMax(min_x, max_x), MinMaxResult::MinMax(min_y, max_y)) => {
|
(MinMaxResult::MinMax(min_x, max_x), MinMaxResult::MinMax(min_y, max_y)) => {
|
||||||
((min_x.x, min_y.y), (max_x.x, max_y.y))
|
((min_x.x, min_y.y), (max_x.x, max_y.y))
|
||||||
},
|
}
|
||||||
|
|
||||||
_ => panic!("Cannot determine bounding box")
|
_ => panic!("Cannot determine bounding box")
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
fn box_count_2d(data: &Vec<Grid2D>, box_number: u32) -> usize {
|
fn box_count_2d(data: &Vec<Grid2D>, box_number: u32) -> (f64, usize) {
|
||||||
let n = data.len();
|
let ((x_min, y_min), (x_max, y_max)) = bb(data);
|
||||||
let ((x_min, x_max), (y_min, y_max)) = bb(data);
|
|
||||||
|
|
||||||
let x_range = (x_max - x_min) as f64;
|
let x_range = (x_max - x_min) as f64;
|
||||||
let y_range = (y_max - y_min) as f64;
|
let y_range = (y_max - y_min) as f64;
|
||||||
|
|
||||||
let w: f64 = x_range / (box_number as f64);
|
let w: f64 = x_range / (box_number as f64);
|
||||||
|
|
||||||
data.iter()
|
let boxes_occupied = data.iter()
|
||||||
.map(|Grid2D { x, y }| [((x - x_min) as f64 / w) as u32, ((y - y_min) as f64 / w) as u32])
|
.map(|Grid2D { x, y }| [((x - x_min) as f64 / w) as i32, ((y - y_min) as f64 / w) as i32])
|
||||||
.unique()
|
.unique()
|
||||||
.count()
|
.count();
|
||||||
|
|
||||||
|
(w, boxes_occupied)
|
||||||
}
|
}
|
||||||
|
|
||||||
fn box_count_3d(data: &Vec<Grid3D>, size: u32) -> usize {
|
fn box_count_3d(data: &Vec<Grid3D>, size: u32) -> usize {
|
||||||
@ -110,6 +111,25 @@ fn box_count_nd<const N: usize>(data: &Vec<[f32; N]>, size: u32) -> usize {
|
|||||||
.count();
|
.count();
|
||||||
}
|
}
|
||||||
|
|
||||||
pub fn main(cli: &BoxCountCli) {
|
#[derive(Serialize)]
|
||||||
let particles = read(&cli.path, cli.format);
|
struct FDRow {
|
||||||
|
w: f64,
|
||||||
|
n_occupied: usize,
|
||||||
|
}
|
||||||
|
|
||||||
|
pub(crate) fn main(cli: &BoxCountCli) {
|
||||||
|
let particles: Vec<Grid2D> = read(&cli.path, cli.format);
|
||||||
|
let n_particles = dbg!(particles.len());
|
||||||
|
let box_side_counts = 1..500;
|
||||||
|
|
||||||
|
let mut writer = csv::Writer::from_path(&cli.output)
|
||||||
|
.expect("Unable to create csv");
|
||||||
|
|
||||||
|
box_side_counts
|
||||||
|
.map(|box_side_count| box_count_2d(&particles, box_side_count))
|
||||||
|
// .filter(|(w, n_occupied)| *n_occupied < n_particles) // Remove saturated values
|
||||||
|
.map(|(w, n_occupied)| FDRow { w, n_occupied })
|
||||||
|
.for_each(|row| writer.serialize(row).expect("Failed to write row"));
|
||||||
|
|
||||||
|
writer.flush().unwrap();
|
||||||
}
|
}
|
||||||
|
|||||||
@ -1,3 +1,4 @@
|
|||||||
|
use std::fs::File;
|
||||||
use std::path::Path;
|
use std::path::Path;
|
||||||
use serde::de::DeserializeOwned;
|
use serde::de::DeserializeOwned;
|
||||||
use crate::cli::cli::OutputFormat;
|
use crate::cli::cli::OutputFormat;
|
||||||
|
|||||||
@ -12,8 +12,10 @@ use serde::de::DeserializeOwned;
|
|||||||
use serde::Deserialize;
|
use serde::Deserialize;
|
||||||
use svg::Node;
|
use svg::Node;
|
||||||
use svg::node::element::Rectangle;
|
use svg::node::element::Rectangle;
|
||||||
|
use crate::RenderCli;
|
||||||
use crate::system::Position;
|
use crate::system::Position;
|
||||||
use crate::system::spaces::hexagonal::HexPosition;
|
use crate::system::spaces::hexagonal::HexPosition;
|
||||||
|
use crate::tools::read;
|
||||||
|
|
||||||
#[derive(Debug, Parser)]
|
#[derive(Debug, Parser)]
|
||||||
struct Args {
|
struct Args {
|
||||||
@ -60,30 +62,10 @@ impl ToSvg for HexPosition {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
fn read_json<T: Position>(args: &Args) -> Vec<T> where T: DeserializeOwned {
|
pub(crate) fn main(args: &RenderCli) {
|
||||||
serde_json::from_reader::<_, Vec<HistoryLine<T>>>(File::open(&args.path).expect("Failed to open file"))
|
let positions: Vec<Grid2D> = read::<Grid2D>(&args.path, args.format);
|
||||||
.expect("Failed to read json")
|
|
||||||
.iter()
|
|
||||||
.map(|l| (l.position.clone()))
|
|
||||||
.collect::<Vec<_>>()
|
|
||||||
}
|
|
||||||
|
|
||||||
fn read_csv<T: Position>(args: &Args) -> Vec<T> where T: DeserializeOwned {
|
let size: i32 = args.image_size as i32;
|
||||||
csv::Reader::from_path(&args.path).expect("Failed to read positions csv").deserialize::<T>()
|
|
||||||
.collect::<Result<Vec<T>, _>>()
|
|
||||||
.unwrap()
|
|
||||||
}
|
|
||||||
|
|
||||||
fn main() {
|
|
||||||
let args = Args::parse();
|
|
||||||
dbg!(&args);
|
|
||||||
|
|
||||||
let positions: Vec<Grid2D> = match args.format {
|
|
||||||
OutputFormat::FullDataJson => read_json::<Grid2D>(&args),
|
|
||||||
OutputFormat::Positions => read_csv::<Grid2D>(&args),
|
|
||||||
};
|
|
||||||
|
|
||||||
let size: i32 = 800;
|
|
||||||
let max_x = positions.iter().max_by(|a, b| a.x.abs().cmp(&b.x.abs())).unwrap().x.abs();
|
let max_x = positions.iter().max_by(|a, b| a.x.abs().cmp(&b.x.abs())).unwrap().x.abs();
|
||||||
let max_y = positions.iter().max_by(|a, b| a.y.abs().cmp(&b.y.abs())).unwrap().y.abs();
|
let max_y = positions.iter().max_by(|a, b| a.y.abs().cmp(&b.y.abs())).unwrap().y.abs();
|
||||||
let max_size = max_x.max(max_y) * size;
|
let max_size = max_x.max(max_y) * size;
|
||||||
@ -105,5 +87,5 @@ fn main() {
|
|||||||
svg.append(position.to_svg(size));
|
svg.append(position.to_svg(size));
|
||||||
}
|
}
|
||||||
|
|
||||||
svg::write(File::create(args.output).unwrap(), &svg).unwrap();
|
svg::write(File::create(&args.output).unwrap(), &svg).unwrap();
|
||||||
}
|
}
|
||||||
|
|||||||
@ -2,7 +2,7 @@
|
|||||||
#![feature(let_chains)]
|
#![feature(let_chains)]
|
||||||
|
|
||||||
use std::fs::File;
|
use std::fs::File;
|
||||||
use std::path::{Path, PathBuf};
|
use std::path::PathBuf;
|
||||||
use anyhow::Context;
|
use anyhow::Context;
|
||||||
use crate::cli::cli::OutputFormat;
|
use crate::cli::cli::OutputFormat;
|
||||||
use crate::system::model::HistoryLine;
|
use crate::system::model::HistoryLine;
|
||||||
@ -25,9 +25,24 @@ enum ToolsCli {
|
|||||||
BoxCount(BoxCountCli)
|
BoxCount(BoxCountCli)
|
||||||
}
|
}
|
||||||
|
|
||||||
|
#[derive(clap::ValueEnum, Clone, Debug, Copy)]
|
||||||
|
enum Space {
|
||||||
|
Grid2D,
|
||||||
|
}
|
||||||
|
|
||||||
#[derive(Debug, Args)]
|
#[derive(Debug, Args)]
|
||||||
struct RenderCli {
|
struct RenderCli {
|
||||||
|
#[arg(value_enum, short, long, default_value_t = OutputFormat::Positions)]
|
||||||
|
format: OutputFormat,
|
||||||
|
|
||||||
|
#[arg(value_enum, short, long, default_value_t = Space::Grid2D)]
|
||||||
|
space: Space,
|
||||||
|
|
||||||
|
path: PathBuf,
|
||||||
|
output: PathBuf,
|
||||||
|
|
||||||
|
#[arg(short, long, default_value_t = 800)]
|
||||||
|
image_size: u32,
|
||||||
}
|
}
|
||||||
|
|
||||||
#[derive(Debug, Args)]
|
#[derive(Debug, Args)]
|
||||||
@ -35,6 +50,7 @@ struct BoxCountCli {
|
|||||||
#[arg(value_enum, short, long, default_value_t = OutputFormat::Positions)]
|
#[arg(value_enum, short, long, default_value_t = OutputFormat::Positions)]
|
||||||
format: OutputFormat,
|
format: OutputFormat,
|
||||||
path: PathBuf,
|
path: PathBuf,
|
||||||
|
output: PathBuf,
|
||||||
}
|
}
|
||||||
|
|
||||||
fn main() {
|
fn main() {
|
||||||
@ -42,7 +58,7 @@ fn main() {
|
|||||||
dbg!(&args);
|
dbg!(&args);
|
||||||
|
|
||||||
match args {
|
match args {
|
||||||
ToolsCli::Render(_) => {}
|
ToolsCli::Render(cli) => tools::render::main(&cli),
|
||||||
ToolsCli::BoxCount(cli) => tools::boxcount::main(&cli),
|
ToolsCli::BoxCount(cli) => tools::boxcount::main(&cli),
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
Loading…
Reference in New Issue
Block a user