début plotting, pour l'instant ça marche pas

This commit is contained in:
jfelderh
2024-10-28 15:43:30 +01:00
parent 33de1a4778
commit fe470cf1c1
5 changed files with 92 additions and 9 deletions

16
Cargo.lock generated
View File

@@ -60,6 +60,12 @@ dependencies = [
"memchr",
]
[[package]]
name = "either"
version = "1.13.0"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "60b1af1c220855b6ceac025d3f6ecdd2b7c4894bfe9cd9bda4fbb4bc7c0d4cf0"
[[package]]
name = "getrandom"
version = "0.2.10"
@@ -71,6 +77,15 @@ dependencies = [
"wasi",
]
[[package]]
name = "itertools"
version = "0.13.0"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "413ee7dfc52ee1a4949ceeb7dbc8a33f2d6c088194d9f922fb8318faf1f01186"
dependencies = [
"either",
]
[[package]]
name = "itoa"
version = "1.0.9"
@@ -149,6 +164,7 @@ version = "0.1.0"
dependencies = [
"argh",
"csv",
"itertools",
"rand",
"rand_chacha",
"serde",

View File

@@ -8,6 +8,7 @@ edition = "2021"
[dependencies]
argh = "0.1.12"
csv = "1.2.2"
itertools = "0.13.0"
rand = "0.8.5"
rand_chacha = "0.3.1"
serde = "1.0.188"

View File

@@ -1,20 +1,66 @@
use super::repartition::*;
use std::fs;
use std::process::Command;
const FORMAT_TEXT: &'static str = "<html>
use super::repartition::*;
use itertools::Itertools;
impl Repartition {
pub fn to_json(&self) -> String {
let participants = self
.0
.iter()
.flat_map(|t| vec![t.from.clone(), t.to.clone()])
.dedup()
.collect_vec();
let mut str_nodes = String::new();
for p in participants {
str_nodes += &format!(
"{{
\"data\": {{
\"id\":\"{}\",
\"label\":\"{}\"
}},
}},",
p.name, p.name
);
}
let mut str_edges = String::new();
for t in &self.0 {
str_edges += &format!(
"{{
\"data\": {{
\"id\":\"{}-{}\",
\"label\":\"{}\",
\"source\":\"{}\",
\"target\":\"{}\",
}}
}},",
t.from.name,
t.to.name,
t.amount as f32 / 100.,
t.from.name,
t.to.name,
)
}
"[".to_owned() + &str_nodes + "," + &str_edges + "]"
}
}
const FORMAT_STRING: &'static str = "<html>
<head>
<script src=\"/home/jfelderh/Prog/Repartition Alpes/cytoscape.min.js\"></script>
</head>
<body>
<div id=\"graph\" style=\"width: auto;height: 500px;\"></div>
<h3>Balance totale (doit être égal à zéro) : {}€</h3>
<h3>Balance totale (doit être égal à zéro) : TOTAL_BALANCE €</h3>
<script type=\"text/javascript\">
var cy = cytoscape({
container: document.getElementById('graph'), // container to render in
elements:{},
elements:ELEMENTS,
style: [ // the stylesheet for the graph
{
@@ -48,3 +94,15 @@ style: [ // the stylesheet for the graph
</body>
";
use super::repartition::*;
pub fn plot_repartition(rep: &Repartition) {
let text_html = FORMAT_STRING
.to_string()
.replace("TOTAL_BALANCE", &rep.total_balance().to_string())
.replace("ELEMENTS", &rep.to_json());
fs::write("/tmp/repartition.html", text_html).expect("Could not write into /tmp/");
Command::new("firefox")
.arg("/tmp/repartition.html")
.output()
.expect("Could not run firefox");
}

View File

@@ -37,12 +37,16 @@ fn main() {
let repartition_file = fs::File::open(filename).expect("not able to read file");
let mut csv_reader = csv::ReaderBuilder::new()
.has_headers(false)
.delimiter(b';')
.delimiter(b',')
.from_reader(repartition_file);
let user_list = csv_reader
.records()
.map(Result::unwrap)
.map(|r| {
dbg!(&r);
r
})
.map(|record| User {
name: record[0].parse::<String>().unwrap().trim_end().to_string(),
balance_cents: (record[1].parse::<f64>().unwrap() * 100.) as i32,
@@ -67,9 +71,11 @@ fn main() {
serde_json::to_string_pretty(&best_repartition).unwrap()
);
} else if let Some(filename) = args.transfert_list_filename {
dbg!(&filename);
let repart: Repartition =
serde_json::from_reader(fs::File::open(filename).expect("not able to read file"))
.expect("unable to read file");
io::plot_repartition(&repart);
} else {
println!("No parameter given, exiting");
}

View File

@@ -1,10 +1,10 @@
use std::cmp::min;
use std::{cmp::min, collections::HashSet};
use rand::prelude::*;
use serde::{Deserialize, Serialize};
#[derive(Debug, Clone, Deserialize, Serialize)]
#[derive(Debug, Clone, PartialEq, Eq, Deserialize, Serialize)]
pub struct User {
pub name: String,
pub email: String,
@@ -85,11 +85,13 @@ pub struct Transfer {
}
#[derive(Debug, Deserialize, Serialize)]
pub struct Repartition(Vec<Transfer>);
pub struct Repartition(pub Vec<Transfer>);
type Evaluation = (usize);
impl Repartition {
pub fn total_balance(&self) -> i32 {
self.0.iter().map(|t| t.amount as i32).sum()
}
pub fn evaluate(&self) -> Evaluation {
self.0.len()
}