Starting to convert main_do, statistics, frequency not working
frequency not working, also need to look into perpetual better
This commit is contained in:
123
src/examples.rs
Normal file
123
src/examples.rs
Normal file
@ -0,0 +1,123 @@
|
|||||||
|
use crate::rsprocess::statistics;
|
||||||
|
use crate::rsprocess::structure::RSsystem;
|
||||||
|
use crate::rsprocess::transitions;
|
||||||
|
use crate::rsprocess::translator::Translator;
|
||||||
|
use crate::rsprocess::translator::WithTranslator;
|
||||||
|
use crate::rsprocess::perpetual;
|
||||||
|
|
||||||
|
use std::fs;
|
||||||
|
use std::io;
|
||||||
|
use std::io::prelude::*;
|
||||||
|
use std::env;
|
||||||
|
|
||||||
|
// grammar is defined in main.rs, calling lalrpop_mod! twice, generates twice
|
||||||
|
// the code
|
||||||
|
use super::grammar;
|
||||||
|
|
||||||
|
|
||||||
|
fn read_system(
|
||||||
|
translator: &mut Translator,
|
||||||
|
path: std::path::PathBuf
|
||||||
|
) -> std::io::Result<RSsystem> {
|
||||||
|
// we read the file with a buffer
|
||||||
|
let f = fs::File::open(path.clone())?;
|
||||||
|
let mut buf_reader = io::BufReader::new(f);
|
||||||
|
let mut contents = String::new();
|
||||||
|
buf_reader.read_to_string(&mut contents)?;
|
||||||
|
|
||||||
|
// parse
|
||||||
|
let result = grammar::SystemParser::new().parse(translator, &contents).unwrap();
|
||||||
|
|
||||||
|
Ok(result)
|
||||||
|
}
|
||||||
|
|
||||||
|
// equivalent main_do(stat) or main_do(stat, MissingE)
|
||||||
|
pub fn stats() -> std::io::Result<()> {
|
||||||
|
let mut translator = Translator::new();
|
||||||
|
|
||||||
|
let mut path = env::current_dir()?;
|
||||||
|
// file to read is inside testing/
|
||||||
|
path = path.join("testing/first.system");
|
||||||
|
let system = read_system(&mut translator, path)?;
|
||||||
|
|
||||||
|
|
||||||
|
// print statistics to screan
|
||||||
|
println!("{}", statistics::of_RSsystem(&translator, &system));
|
||||||
|
|
||||||
|
// to write to file:
|
||||||
|
//// path = path.with_extension("stats");
|
||||||
|
//// let mut f = std::fs::File::create(path)?;
|
||||||
|
//// writeln!(f, "{}", statistics::of_RSsystem(translator, &result))?;
|
||||||
|
|
||||||
|
Ok(())
|
||||||
|
}
|
||||||
|
|
||||||
|
// equivalent to main_do(target, E)
|
||||||
|
pub fn target() -> std::io::Result<()> {
|
||||||
|
let mut translator = Translator::new();
|
||||||
|
|
||||||
|
let mut path = env::current_dir()?;
|
||||||
|
// file to read is inside testing/
|
||||||
|
path = path.join("testing/first.system");
|
||||||
|
let system = read_system(&mut translator, path)?;
|
||||||
|
|
||||||
|
// the system needs to terminate to return
|
||||||
|
let res = match transitions::target(&system) {
|
||||||
|
Ok(o) => o,
|
||||||
|
Err(e) => {println!("Error computing target: {e}"); return Ok(());}
|
||||||
|
};
|
||||||
|
|
||||||
|
println!("After {} steps we arrive at state:\n{}",
|
||||||
|
res.0,
|
||||||
|
WithTranslator::from_RSset(&translator, &res.1));
|
||||||
|
|
||||||
|
Ok(())
|
||||||
|
}
|
||||||
|
|
||||||
|
// equivalent to main_do(run,Es)
|
||||||
|
pub fn run() -> std::io::Result<()> {
|
||||||
|
let mut translator = Translator::new();
|
||||||
|
|
||||||
|
let mut path = env::current_dir()?;
|
||||||
|
// file to read is inside testing/
|
||||||
|
path = path.join("testing/first.system");
|
||||||
|
let system = read_system(&mut translator, path)?;
|
||||||
|
|
||||||
|
// the system needs to terminate to return
|
||||||
|
let res = match transitions::run_separated(&system) {
|
||||||
|
Ok(o) => o,
|
||||||
|
Err(e) => {println!("Error computing target: {e}"); return Ok(());}
|
||||||
|
};
|
||||||
|
|
||||||
|
println!("The trace is composed of the entities:");
|
||||||
|
|
||||||
|
for (e, _c, _t) in res {
|
||||||
|
println!("{}", WithTranslator::from_RSset(&translator, &e));
|
||||||
|
}
|
||||||
|
|
||||||
|
Ok(())
|
||||||
|
}
|
||||||
|
|
||||||
|
// equivalent to main_do(loop,Es)
|
||||||
|
pub fn hoop() -> std::io::Result<()> {
|
||||||
|
let mut translator = Translator::new();
|
||||||
|
|
||||||
|
let mut path = env::current_dir()?;
|
||||||
|
// file to read is inside testing/
|
||||||
|
path = path.join("testing/first.system");
|
||||||
|
let system = read_system(&mut translator, path)?;
|
||||||
|
|
||||||
|
// we retrieve the id for "x" and use it to find the corresponding loop
|
||||||
|
let res = match perpetual::lollipops_only_loop_named(system, translator.encode("x")) {
|
||||||
|
Some(o) => o,
|
||||||
|
None => {println!("No loop found."); return Ok(());}
|
||||||
|
};
|
||||||
|
|
||||||
|
println!("The loop is composed by the sets:");
|
||||||
|
|
||||||
|
for e in res {
|
||||||
|
println!("{}", WithTranslator::from_RSset(&translator, &e));
|
||||||
|
}
|
||||||
|
|
||||||
|
Ok(())
|
||||||
|
}
|
||||||
198
src/main.rs
198
src/main.rs
@ -1,201 +1,25 @@
|
|||||||
#![allow(unused_imports)]
|
#![allow(unused_imports)]
|
||||||
mod rsprocess;
|
mod rsprocess;
|
||||||
use lalrpop_util::lalrpop_mod;
|
mod examples;
|
||||||
|
|
||||||
use std::{hash::Hash, rc::Rc};
|
use std::{hash::Hash, rc::Rc};
|
||||||
use rsprocess::translator::WithTranslator;
|
use rsprocess::translator::WithTranslator;
|
||||||
// use std::io;
|
|
||||||
|
|
||||||
fn main() -> Result<(), Box<dyn std::error::Error>> {
|
lalrpop_util::lalrpop_mod!(#[allow(clippy::uninlined_format_args)] pub grammar, "/rsprocess/grammar.rs");
|
||||||
lalrpop_mod!(grammar, "/rsprocess/grammar.rs");
|
|
||||||
|
|
||||||
let mut translator = rsprocess::translator::Translator::new();
|
fn main() -> std::io::Result<()> {
|
||||||
|
|
||||||
// let mut buffer = String::new();
|
// let now = std::time::Instant::now();
|
||||||
// let i = io::stdin();
|
// std::thread::sleep(std::time::Duration::new(2, 0));
|
||||||
// i.read_line(&mut buffer).expect("Can't read stdin");
|
// println!("{}", now.elapsed().as_micros());
|
||||||
|
|
||||||
// let result = grammar::SetParser::new().parse(&mut translator, &buffer).unwrap();
|
examples::stats()?;
|
||||||
|
|
||||||
|
examples::hoop()?;
|
||||||
|
|
||||||
// -------------------------------------------------------------------------
|
examples::target()?;
|
||||||
// let reactants = grammar::SetParser::new().parse(&mut translator, "{a}").unwrap();
|
|
||||||
// let inihibitors = grammar::SetParser::new().parse(&mut translator, "{c}").unwrap();
|
|
||||||
// let products = grammar::SetParser::new().parse(&mut translator, "{a,c}").unwrap();
|
|
||||||
|
|
||||||
// let process1 = rsprocess::structure::RSreaction::from(reactants, inihibitors, products);
|
examples::run()?;
|
||||||
|
|
||||||
// let reactants = grammar::SetParser::new().parse(&mut translator, "{b}").unwrap();
|
|
||||||
// let inihibitors = grammar::SetParser::new().parse(&mut translator, "{c}").unwrap();
|
|
||||||
// let products = grammar::SetParser::new().parse(&mut translator, "{b,c}").unwrap();
|
|
||||||
|
|
||||||
// let process2 = rsprocess::structure::RSreaction::from(reactants, inihibitors, products);
|
|
||||||
|
|
||||||
// let current_state = grammar::SetParser::new().parse(&mut translator, "{b}").unwrap();
|
|
||||||
|
|
||||||
// println!("{:?}", rsprocess::classical::compute_all(¤t_state, vec![&process1, &process2]));
|
|
||||||
|
|
||||||
|
|
||||||
// -------------------------------------------------------------------------
|
|
||||||
// let env = grammar::EnvironmentParser::new().parse(&mut translator, "[x = {a}.{b}.x , y = ({a,c}.y + {b,c}.y)]").unwrap();
|
|
||||||
// let process = grammar::ContextParser::new().parse(&mut translator, "[({a}.nil + x + y)]").unwrap();
|
|
||||||
|
|
||||||
// println!("{:?}", rsprocess::transitions::unfold(&env, &process));
|
|
||||||
|
|
||||||
// println!("--------------------");
|
|
||||||
|
|
||||||
// println!("{:?}", env);
|
|
||||||
|
|
||||||
|
|
||||||
// -------------------------------------------------------------------------
|
|
||||||
// allTransitions(sys([],[a,b],[],[react([a],[c],[a]),react([b],[d],[b])]) , Moves).
|
|
||||||
|
|
||||||
// let env = grammar::EnvironmentParser::new().parse(&mut translator, "[]").unwrap();
|
|
||||||
// let process = grammar::ContextParser::new().parse(&mut translator, "[]").unwrap();
|
|
||||||
|
|
||||||
// let sys = rsprocess::structure::RSsystem::from(Rc::new(*env),
|
|
||||||
// rsprocess::structure::RSset::from(vec![translator.encode("a"),
|
|
||||||
// translator.encode("b")]),
|
|
||||||
// *process,
|
|
||||||
// Rc::new(vec![
|
|
||||||
// rsprocess::structure::RSreaction::from(
|
|
||||||
// rsprocess::structure::RSset::from(vec![translator.encode("a")]),
|
|
||||||
// rsprocess::structure::RSset::from(vec![translator.encode("c")]),
|
|
||||||
// rsprocess::structure::RSset::from(vec![translator.encode("a")])
|
|
||||||
// ),
|
|
||||||
// rsprocess::structure::RSreaction::from(
|
|
||||||
// rsprocess::structure::RSset::from(vec![translator.encode("b")]),
|
|
||||||
// rsprocess::structure::RSset::from(vec![translator.encode("d")]),
|
|
||||||
// rsprocess::structure::RSset::from(vec![translator.encode("b")])
|
|
||||||
// )
|
|
||||||
// ]));
|
|
||||||
|
|
||||||
|
|
||||||
// println!("all_transitions: {:?}", rsprocess::transitions::all_transitions(&sys));
|
|
||||||
// -------------------------------------------------------------------------
|
|
||||||
// parse_ctx("[({a}.nil + {b}.nil)]",Ks) , allTransitions(sys([],[],Ks,[react([a],[c],[a]),react([b],[d],[b])]),Moves).
|
|
||||||
// let env = grammar::EnvironmentParser::new().parse(&mut translator, "[]").unwrap();
|
|
||||||
// let process = grammar::ContextParser::new().parse(&mut translator, "[({a}.nil + {b}.nil)]").unwrap();
|
|
||||||
|
|
||||||
// let sys = rsprocess::structure::RSsystem::from(Rc::new(*env),
|
|
||||||
// rsprocess::structure::RSset::from(vec![]),
|
|
||||||
// *process,
|
|
||||||
// Rc::new(vec![
|
|
||||||
// rsprocess::structure::RSreaction::from(
|
|
||||||
// rsprocess::structure::RSset::from(vec![translator.encode("a")]),
|
|
||||||
// rsprocess::structure::RSset::from(vec![translator.encode("c")]),
|
|
||||||
// rsprocess::structure::RSset::from(vec![translator.encode("a")])
|
|
||||||
// ),
|
|
||||||
// rsprocess::structure::RSreaction::from(
|
|
||||||
// rsprocess::structure::RSset::from(vec![translator.encode("b")]),
|
|
||||||
// rsprocess::structure::RSset::from(vec![translator.encode("d")]),
|
|
||||||
// rsprocess::structure::RSset::from(vec![translator.encode("b")])
|
|
||||||
// )
|
|
||||||
// ]));
|
|
||||||
|
|
||||||
|
|
||||||
// println!("all_transitions: {:?}", rsprocess::transitions::all_transitions(&sys));
|
|
||||||
|
|
||||||
// -------------------------------------------------------------------------
|
|
||||||
// parse_ctx("[({a}.nil + {b}.nil),({c}.nil + {d}.nil)]",Ks) , allTransitions(sys([],[],Ks,[react([a],[c],[a]),react([b],[d],[b])]),Moves).
|
|
||||||
// let env = grammar::EnvironmentParser::new().parse(&mut translator, "[]").unwrap();
|
|
||||||
// let process = grammar::ContextParser::new().parse(&mut translator, "[({a}.nil + {b}.nil),({c}.nil + {d}.nil)]").unwrap();
|
|
||||||
|
|
||||||
// let sys = rsprocess::structure::RSsystem::from(Rc::new(*env),
|
|
||||||
// rsprocess::structure::RSset::from(vec![]),
|
|
||||||
// *process,
|
|
||||||
// Rc::new(vec![
|
|
||||||
// rsprocess::structure::RSreaction::from(
|
|
||||||
// rsprocess::structure::RSset::from(vec![translator.encode("a")]),
|
|
||||||
// rsprocess::structure::RSset::from(vec![translator.encode("c")]),
|
|
||||||
// rsprocess::structure::RSset::from(vec![translator.encode("a")])
|
|
||||||
// ),
|
|
||||||
// rsprocess::structure::RSreaction::from(
|
|
||||||
// rsprocess::structure::RSset::from(vec![translator.encode("b")]),
|
|
||||||
// rsprocess::structure::RSset::from(vec![translator.encode("d")]),
|
|
||||||
// rsprocess::structure::RSset::from(vec![translator.encode("b")])
|
|
||||||
// )
|
|
||||||
// ]));
|
|
||||||
|
|
||||||
// let it = rsprocess::transitions::iterator_transitions(&sys)?;
|
|
||||||
|
|
||||||
// for (n, i) in it.into_iter().enumerate() {
|
|
||||||
// println!("next i - {n}: {:?}", i);
|
|
||||||
// println!("--------------------");
|
|
||||||
// }
|
|
||||||
|
|
||||||
// -------------------------------------------------------------------------
|
|
||||||
// let env = grammar::EnvironmentParser::new().parse(&mut translator, "[]").unwrap();
|
|
||||||
// let process = grammar::ContextParser::new().parse(&mut translator, "[({a}.nil + {b}.nil),({c}.nil + {d}.nil)]").unwrap();
|
|
||||||
|
|
||||||
// let sys = rsprocess::structure::RSsystem::from(Rc::new(*env),
|
|
||||||
// rsprocess::structure::RSset::from(vec![]),
|
|
||||||
// *process,
|
|
||||||
// Rc::new(vec![
|
|
||||||
// rsprocess::structure::RSreaction::from(
|
|
||||||
// rsprocess::structure::RSset::from(vec![translator.encode("a")]),
|
|
||||||
// rsprocess::structure::RSset::from(vec![translator.encode("c")]),
|
|
||||||
// rsprocess::structure::RSset::from(vec![translator.encode("a")])
|
|
||||||
// ),
|
|
||||||
// rsprocess::structure::RSreaction::from(
|
|
||||||
// rsprocess::structure::RSset::from(vec![translator.encode("b")]),
|
|
||||||
// rsprocess::structure::RSset::from(vec![translator.encode("d")]),
|
|
||||||
// rsprocess::structure::RSset::from(vec![translator.encode("b")])
|
|
||||||
// )
|
|
||||||
// ]));
|
|
||||||
// println!("{:?}", rsprocess::transitions::run_separated(&sys));
|
|
||||||
|
|
||||||
// -------------------------------------------------------------------------
|
|
||||||
// list_to_assoc([x-pre([a, b], rec(x)), y-pre([d, e], rec(y))], Ass),
|
|
||||||
// lollipop(sys(Ass, [a, b, c, d], [], [react([a], [c], [a]), react([d], [f], [d])]), Prefix, Loop).
|
|
||||||
|
|
||||||
let env = grammar::EnvironmentParser::new().parse(&mut translator, "[x = {a,b}.x]").unwrap();
|
|
||||||
let process = grammar::ContextParser::new().parse(&mut translator, "[]").unwrap();
|
|
||||||
|
|
||||||
let sys = rsprocess::structure::RSsystem::from(Rc::new(*env),
|
|
||||||
rsprocess::structure::RSset::from(vec![translator.encode("a"),
|
|
||||||
translator.encode("b"),
|
|
||||||
translator.encode("c"),
|
|
||||||
translator.encode("d")]),
|
|
||||||
*process,
|
|
||||||
Rc::new(vec![
|
|
||||||
rsprocess::structure::RSreaction::from(
|
|
||||||
rsprocess::structure::RSset::from(vec![translator.encode("a")]),
|
|
||||||
rsprocess::structure::RSset::from(vec![translator.encode("c")]),
|
|
||||||
rsprocess::structure::RSset::from(vec![translator.encode("a")])
|
|
||||||
),
|
|
||||||
rsprocess::structure::RSreaction::from(
|
|
||||||
rsprocess::structure::RSset::from(vec![translator.encode("d")]),
|
|
||||||
rsprocess::structure::RSset::from(vec![translator.encode("f")]),
|
|
||||||
rsprocess::structure::RSset::from(vec![translator.encode("d")])
|
|
||||||
)
|
|
||||||
]));
|
|
||||||
|
|
||||||
let res = rsprocess::perpetual::lollipops(sys.clone());
|
|
||||||
|
|
||||||
println!("res:");
|
|
||||||
for (prefix, hoop) in res {
|
|
||||||
print!("prefix: ");
|
|
||||||
for p in prefix {
|
|
||||||
print!("{}, ", WithTranslator::from_RSset(&translator, &p));
|
|
||||||
}
|
|
||||||
print!("\nhoop: ");
|
|
||||||
for l in hoop {
|
|
||||||
print!("{}, ", WithTranslator::from_RSset(&translator, &l));
|
|
||||||
}
|
|
||||||
println!();
|
|
||||||
}
|
|
||||||
|
|
||||||
let res = rsprocess::perpetual::lollipops_only_loop(sys);
|
|
||||||
|
|
||||||
println!("res:");
|
|
||||||
for hoop in res {
|
|
||||||
print!("hoop: ");
|
|
||||||
for l in hoop {
|
|
||||||
print!("{}, ", WithTranslator::from_RSset(&translator, &l));
|
|
||||||
}
|
|
||||||
println!();
|
|
||||||
}
|
|
||||||
|
|
||||||
// -------------------------------------------------------------------------
|
|
||||||
Ok(())
|
Ok(())
|
||||||
}
|
}
|
||||||
|
|||||||
@ -1,11 +1,22 @@
|
|||||||
use std::rc::Rc;
|
use std::rc::Rc;
|
||||||
use std::str::FromStr;
|
use std::str::FromStr;
|
||||||
use lalrpop_util::ParseError;
|
use lalrpop_util::ParseError;
|
||||||
use crate::rsprocess::structure::{RSset, RSprocess, RSenvironment, RSassert, RSassertOp, RSBHML};
|
use crate::rsprocess::structure::{RSset,
|
||||||
|
RSprocess,
|
||||||
|
RSenvironment,
|
||||||
|
RSassert,
|
||||||
|
RSassertOp,
|
||||||
|
RSBHML,
|
||||||
|
RSsystem,
|
||||||
|
RSreaction};
|
||||||
use crate::rsprocess::translator::{Translator, IdType};
|
use crate::rsprocess::translator::{Translator, IdType};
|
||||||
|
|
||||||
grammar(translator: &mut Translator);
|
grammar(translator: &mut Translator);
|
||||||
|
|
||||||
|
// -----------------------------------------------------------------------------
|
||||||
|
// Helpers
|
||||||
|
// -----------------------------------------------------------------------------
|
||||||
|
|
||||||
// matches words (letter followed by numbers, letters or _)
|
// matches words (letter followed by numbers, letters or _)
|
||||||
Literal = { r"[[:alpha:]][[:word:]]*" };
|
Literal = { r"[[:alpha:]][[:word:]]*" };
|
||||||
|
|
||||||
@ -26,7 +37,9 @@ Separeted<T, C>: Vec<T> = {
|
|||||||
}
|
}
|
||||||
};
|
};
|
||||||
|
|
||||||
// ----- SetParser -----
|
// -----------------------------------------------------------------------------
|
||||||
|
// SetParser
|
||||||
|
// -----------------------------------------------------------------------------
|
||||||
pub Set: RSset = {
|
pub Set: RSset = {
|
||||||
<s: Set_of_entities> => s
|
<s: Set_of_entities> => s
|
||||||
};
|
};
|
||||||
@ -38,18 +51,31 @@ Set_of_entities: RSset = {
|
|||||||
RSset::from(t.into_iter().map(|t| translator.encode(t)).collect::<Vec<_>>())
|
RSset::from(t.into_iter().map(|t| translator.encode(t)).collect::<Vec<_>>())
|
||||||
};
|
};
|
||||||
|
|
||||||
// ----- ContextParser -----
|
|
||||||
pub Context: Box<RSprocess> = {
|
|
||||||
// "[" "]" => Box::new(RSprocess::Nill),
|
|
||||||
// "[" <t: CTX_process> "]" => Box::new(t),
|
|
||||||
// "[" <t: Separeted<Boxed_CTX_process, ",">> "]" =>
|
|
||||||
// Box::new(RSprocess::NondeterministicChoice{ children: t })
|
|
||||||
|
|
||||||
"[" "]" => Box::new(RSprocess::NondeterministicChoice{ children: vec![] }),
|
// -----------------------------------------------------------------------------
|
||||||
|
// ReactionParser
|
||||||
|
// -----------------------------------------------------------------------------
|
||||||
|
|
||||||
|
pub Reactions: Vec<RSreaction> = {
|
||||||
|
"(" ")" => vec![],
|
||||||
|
"(" <r: Reaction> ")" => vec![r],
|
||||||
|
"(" <s: Separeted<Reaction, ";">> ")" => s
|
||||||
|
}
|
||||||
|
|
||||||
|
Reaction: RSreaction = {
|
||||||
|
"[" <r: Set> "," <i: Set> "," <p: Set> "]" => RSreaction::from(r, i, p),
|
||||||
|
"[" "r:" <r: Set> "," "i:" <i: Set> "," "p:" <p: Set> "]" => RSreaction::from(r, i, p),
|
||||||
|
}
|
||||||
|
|
||||||
|
// -----------------------------------------------------------------------------
|
||||||
|
// ContextParser
|
||||||
|
// -----------------------------------------------------------------------------
|
||||||
|
pub Context: RSprocess = {
|
||||||
|
"[" "]" => RSprocess::NondeterministicChoice{ children: vec![] },
|
||||||
"[" <t: CTX_process> "]" =>
|
"[" <t: CTX_process> "]" =>
|
||||||
Box::new(RSprocess::NondeterministicChoice{children: vec![Rc::new(t)]}),
|
RSprocess::NondeterministicChoice{children: vec![Rc::new(t)]},
|
||||||
"[" <t: Separeted<Boxed_CTX_process, ",">> "]" =>
|
"[" <t: Separeted<Boxed_CTX_process, ",">> "]" =>
|
||||||
Box::new(RSprocess::NondeterministicChoice{ children: t })
|
RSprocess::NondeterministicChoice{ children: t }
|
||||||
};
|
};
|
||||||
|
|
||||||
Boxed_CTX_process: Rc<RSprocess> = {
|
Boxed_CTX_process: Rc<RSprocess> = {
|
||||||
@ -71,7 +97,9 @@ CTX_process: RSprocess = {
|
|||||||
RSprocess::RecursiveIdentifier{ identifier: translator.encode(identifier) }
|
RSprocess::RecursiveIdentifier{ identifier: translator.encode(identifier) }
|
||||||
};
|
};
|
||||||
|
|
||||||
// ----- EnvironmentParser -----
|
// -----------------------------------------------------------------------------
|
||||||
|
// EnvironmentParser
|
||||||
|
// -----------------------------------------------------------------------------
|
||||||
pub Environment: Box<RSenvironment> = {
|
pub Environment: Box<RSenvironment> = {
|
||||||
"[" "]" => Box::new(RSenvironment::new()),
|
"[" "]" => Box::new(RSenvironment::new()),
|
||||||
"[" <t:Env_term> "]" => Box::new(RSenvironment::from(vec![t])),
|
"[" <t:Env_term> "]" => Box::new(RSenvironment::from(vec![t])),
|
||||||
@ -83,7 +111,9 @@ Env_term: (IdType, RSprocess) = {
|
|||||||
(translator.encode(identifier), k)
|
(translator.encode(identifier), k)
|
||||||
};
|
};
|
||||||
|
|
||||||
// ----- AssertParser -----
|
// -----------------------------------------------------------------------------
|
||||||
|
// AssertParser
|
||||||
|
// -----------------------------------------------------------------------------
|
||||||
pub Assert: Box<RSassert> = {
|
pub Assert: Box<RSassert> = {
|
||||||
<f: Formula_Assert> => Box::new(f)
|
<f: Formula_Assert> => Box::new(f)
|
||||||
};
|
};
|
||||||
@ -104,7 +134,9 @@ Formula_Assert: RSassert = {
|
|||||||
"?" "inP" => RSassert::NonEmpty(RSassertOp::InP),
|
"?" "inP" => RSassert::NonEmpty(RSassertOp::InP),
|
||||||
};
|
};
|
||||||
|
|
||||||
// ----- BHMLParser -----
|
// -----------------------------------------------------------------------------
|
||||||
|
// BHMLParser
|
||||||
|
// -----------------------------------------------------------------------------
|
||||||
pub BHML: Box<RSBHML> = {
|
pub BHML: Box<RSBHML> = {
|
||||||
<g: Formula_BHML> => Box::new(g)
|
<g: Formula_BHML> => Box::new(g)
|
||||||
};
|
};
|
||||||
@ -119,3 +151,19 @@ Formula_BHML: RSBHML = {
|
|||||||
"[" <f: Formula_Assert> "]" <g: Formula_BHML> =>
|
"[" <f: Formula_Assert> "]" <g: Formula_BHML> =>
|
||||||
RSBHML::Box(Box::new(f), Box::new(g)),
|
RSBHML::Box(Box::new(f), Box::new(g)),
|
||||||
};
|
};
|
||||||
|
|
||||||
|
|
||||||
|
// -----------------------------------------------------------------------------
|
||||||
|
// File Parsing
|
||||||
|
// -----------------------------------------------------------------------------
|
||||||
|
// system
|
||||||
|
// a system is an environment, a set of entities as initial state, a context and
|
||||||
|
// a set of reaction rules.
|
||||||
|
|
||||||
|
pub System: RSsystem = {
|
||||||
|
"Environment:" <delta: Environment>
|
||||||
|
"Initial Entities:" <available_entities: Set>
|
||||||
|
"Context:" <context_process: Context>
|
||||||
|
"Reactions:" <reaction_rules: Reactions>
|
||||||
|
=> RSsystem::from(delta.into(), available_entities, context_process, Rc::new(reaction_rules))
|
||||||
|
}
|
||||||
|
|||||||
@ -6,3 +6,4 @@ pub mod transitions;
|
|||||||
pub mod perpetual;
|
pub mod perpetual;
|
||||||
pub mod confluence;
|
pub mod confluence;
|
||||||
pub mod frequency;
|
pub mod frequency;
|
||||||
|
pub mod statistics;
|
||||||
|
|||||||
134
src/rsprocess/statistics.rs
Normal file
134
src/rsprocess/statistics.rs
Normal file
@ -0,0 +1,134 @@
|
|||||||
|
#![allow(dead_code)]
|
||||||
|
|
||||||
|
use super::structure::RSset;
|
||||||
|
use super::structure::RSsystem;
|
||||||
|
use super::translator::{Translator, WithTranslator};
|
||||||
|
|
||||||
|
#[allow(non_snake_case)]
|
||||||
|
pub fn of_RSsystem<'a>(translator: &'a Translator, system: &'a RSsystem) -> String {
|
||||||
|
let mut result: String = "Statistics:\n".into();
|
||||||
|
result.push_str(
|
||||||
|
"=============================================================\n"
|
||||||
|
);
|
||||||
|
result.push_str(
|
||||||
|
&format!("the initial state has {} entities:\n",
|
||||||
|
system.get_available_entities().len())
|
||||||
|
);
|
||||||
|
result.push_str(
|
||||||
|
&format!("{}\n",
|
||||||
|
WithTranslator::from_RSset(translator,
|
||||||
|
system.get_available_entities()))
|
||||||
|
);
|
||||||
|
|
||||||
|
let reactants =
|
||||||
|
system
|
||||||
|
.get_reaction_rules()
|
||||||
|
.iter()
|
||||||
|
.fold(RSset::new(), |acc, new| acc.union(new.reactants()));
|
||||||
|
result.push_str(
|
||||||
|
&format!("The reactants are {}:\n{}\n",
|
||||||
|
reactants.len(),
|
||||||
|
WithTranslator::from_RSset(translator, &reactants))
|
||||||
|
);
|
||||||
|
|
||||||
|
let inhibitors =
|
||||||
|
system
|
||||||
|
.get_reaction_rules()
|
||||||
|
.iter()
|
||||||
|
.fold(RSset::new(), |acc, new| acc.union(new.inihibitors()));
|
||||||
|
result.push_str(
|
||||||
|
&format!("The inhibitors are {}:\n{}\n",
|
||||||
|
inhibitors.len(),
|
||||||
|
WithTranslator::from_RSset(translator, &inhibitors))
|
||||||
|
);
|
||||||
|
|
||||||
|
let products =
|
||||||
|
system
|
||||||
|
.get_reaction_rules()
|
||||||
|
.iter()
|
||||||
|
.fold(RSset::new(), |acc, new| acc.union(new.products()));
|
||||||
|
result.push_str(
|
||||||
|
&format!("The products are {}:\n{}\n",
|
||||||
|
products.len(),
|
||||||
|
WithTranslator::from_RSset(translator, &products))
|
||||||
|
);
|
||||||
|
|
||||||
|
|
||||||
|
let total = reactants.union(&inhibitors.union(&products));
|
||||||
|
result.push_str(
|
||||||
|
&format!("The reactions involve {} entities:\n{}\n",
|
||||||
|
total.len(),
|
||||||
|
WithTranslator::from_RSset(translator, &total))
|
||||||
|
);
|
||||||
|
|
||||||
|
let entities_env = system.get_delta().all_elements();
|
||||||
|
result.push_str(
|
||||||
|
&format!("The environment involves {} entities:\n{}\n",
|
||||||
|
entities_env.len(),
|
||||||
|
WithTranslator::from_RSset(translator, &entities_env))
|
||||||
|
);
|
||||||
|
|
||||||
|
let entities_context = system.get_context_process().all_elements();
|
||||||
|
result.push_str(
|
||||||
|
&format!("The context involves {} entities:\n{}\n",
|
||||||
|
entities_context.len(),
|
||||||
|
WithTranslator::from_RSset(translator, &entities_context))
|
||||||
|
);
|
||||||
|
|
||||||
|
let entities_all = total.union(&entities_env)
|
||||||
|
.union(&entities_context)
|
||||||
|
.union(system.get_available_entities());
|
||||||
|
|
||||||
|
result.push_str(
|
||||||
|
&format!("The whole RS involves {} entities:\n{}\n",
|
||||||
|
entities_all.len(),
|
||||||
|
WithTranslator::from_RSset(translator, &entities_all))
|
||||||
|
);
|
||||||
|
|
||||||
|
let possible_e = products.union(system.get_available_entities())
|
||||||
|
.union(&entities_context);
|
||||||
|
let missing_e = reactants.subtraction(&possible_e);
|
||||||
|
result.push_str(
|
||||||
|
&format!("There are {} reactants that will never be available:\n{}\n",
|
||||||
|
missing_e.len(),
|
||||||
|
WithTranslator::from_RSset(translator, &missing_e))
|
||||||
|
);
|
||||||
|
|
||||||
|
let entities_not_needed = entities_context.subtraction(&total);
|
||||||
|
result.push_str(
|
||||||
|
&format!("The context can provide {} entities that will never be used:\n{}\n",
|
||||||
|
entities_not_needed.len(),
|
||||||
|
WithTranslator::from_RSset(translator, &entities_not_needed))
|
||||||
|
);
|
||||||
|
|
||||||
|
result.push_str(
|
||||||
|
&format!("There are {} reactions in total.\n",
|
||||||
|
system.get_reaction_rules().len())
|
||||||
|
);
|
||||||
|
|
||||||
|
let mut admissible_reactions = vec![];
|
||||||
|
let mut nonadmissible_reactions = vec![];
|
||||||
|
|
||||||
|
for reaction in system.get_reaction_rules().iter() {
|
||||||
|
if reaction.reactants().is_disjoint(&missing_e) {
|
||||||
|
admissible_reactions.push(reaction);
|
||||||
|
} else {
|
||||||
|
nonadmissible_reactions.push(reaction);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
result.push_str(
|
||||||
|
&format!("- the applicable reactions are {}.\n",
|
||||||
|
admissible_reactions.len())
|
||||||
|
);
|
||||||
|
|
||||||
|
result.push_str(
|
||||||
|
&format!("- there are {} reactions that will never be enabled.\n",
|
||||||
|
nonadmissible_reactions.len())
|
||||||
|
);
|
||||||
|
result.push_str(
|
||||||
|
"============================================================="
|
||||||
|
);
|
||||||
|
|
||||||
|
result
|
||||||
|
}
|
||||||
@ -1,6 +1,6 @@
|
|||||||
#![allow(dead_code)]
|
#![allow(dead_code)]
|
||||||
|
|
||||||
use std::collections::{BTreeSet, HashMap, HashSet};
|
use std::collections::{BTreeSet, HashMap, HashSet, VecDeque};
|
||||||
use std::hash::{Hash, Hasher};
|
use std::hash::{Hash, Hasher};
|
||||||
use std::rc::Rc;
|
use std::rc::Rc;
|
||||||
use super::translator::{IdType};
|
use super::translator::{IdType};
|
||||||
@ -75,13 +75,31 @@ impl RSset {
|
|||||||
RSset { identifiers: res }
|
RSset { identifiers: res }
|
||||||
}
|
}
|
||||||
|
|
||||||
pub fn hashset(&self) -> &BTreeSet<IdType> {
|
pub fn set(&self) -> &BTreeSet<IdType> {
|
||||||
&self.identifiers
|
&self.identifiers
|
||||||
}
|
}
|
||||||
|
|
||||||
pub fn iter(&self) -> std::collections::btree_set::Iter<'_, IdType> {
|
pub fn iter(&self) -> std::collections::btree_set::Iter<'_, IdType> {
|
||||||
self.identifiers.iter()
|
self.identifiers.iter()
|
||||||
}
|
}
|
||||||
|
|
||||||
|
pub fn len(&self) -> usize {
|
||||||
|
self.identifiers.len()
|
||||||
|
}
|
||||||
|
|
||||||
|
pub fn insert(&mut self, el: IdType) -> bool {
|
||||||
|
self.identifiers.insert(el)
|
||||||
|
}
|
||||||
|
|
||||||
|
pub fn push(&mut self, b: &RSset) {
|
||||||
|
self.identifiers.extend(b.iter())
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
impl Default for RSset {
|
||||||
|
fn default() -> Self {
|
||||||
|
RSset::new()
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
impl IntoIterator for RSset {
|
impl IntoIterator for RSset {
|
||||||
@ -140,6 +158,12 @@ impl RSreaction {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
impl Default for RSreaction {
|
||||||
|
fn default() -> Self {
|
||||||
|
RSreaction::new()
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
// -----------------------------------------------------------------------------
|
// -----------------------------------------------------------------------------
|
||||||
@ -183,8 +207,42 @@ impl RSprocess {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
pub fn all_elements(&self) -> RSset {
|
||||||
|
let mut queue = VecDeque::from([self]);
|
||||||
|
let mut elements = RSset::new();
|
||||||
|
|
||||||
|
while let Some(el) = queue.pop_front() {
|
||||||
|
match el {
|
||||||
|
Self::Nill => {}
|
||||||
|
Self::RecursiveIdentifier { identifier: _ } => {}
|
||||||
|
Self::EntitySet { entities, next_process } => {
|
||||||
|
elements.push(entities);
|
||||||
|
queue.push_back(next_process);
|
||||||
|
}
|
||||||
|
Self::WaitEntity { repeat: _, repeated_process, next_process } => {
|
||||||
|
queue.push_back(repeated_process);
|
||||||
|
queue.push_back(next_process);
|
||||||
|
}
|
||||||
|
Self::Summation { children } => {
|
||||||
|
for c in children {
|
||||||
|
queue.push_back(c);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
Self::NondeterministicChoice { children } => {
|
||||||
|
for c in children {
|
||||||
|
queue.push_back(c);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
elements
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// -----------------------------------------------------------------------------
|
||||||
|
// RSchoices
|
||||||
|
// -----------------------------------------------------------------------------
|
||||||
#[derive(Clone, Debug)]
|
#[derive(Clone, Debug)]
|
||||||
pub struct RSchoices {
|
pub struct RSchoices {
|
||||||
context_moves: Vec<(Rc<RSset>, Rc<RSprocess>)>
|
context_moves: Vec<(Rc<RSset>, Rc<RSprocess>)>
|
||||||
@ -284,6 +342,20 @@ impl RSenvironment {
|
|||||||
pub fn iter(&self) -> std::collections::hash_map::Iter<'_, u32, RSprocess> {
|
pub fn iter(&self) -> std::collections::hash_map::Iter<'_, u32, RSprocess> {
|
||||||
self.definitions.iter()
|
self.definitions.iter()
|
||||||
}
|
}
|
||||||
|
|
||||||
|
pub fn all_elements(&self) -> RSset {
|
||||||
|
let mut acc = RSset::new();
|
||||||
|
for (_, process) in self.definitions.iter() {
|
||||||
|
acc.push(&process.all_elements());
|
||||||
|
}
|
||||||
|
acc
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
impl Default for RSenvironment {
|
||||||
|
fn default() -> Self {
|
||||||
|
RSenvironment::new()
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
impl<const N: usize> From<[(IdType, RSprocess); N]> for RSenvironment {
|
impl<const N: usize> From<[(IdType, RSprocess); N]> for RSenvironment {
|
||||||
@ -352,6 +424,12 @@ impl RSsystem {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
impl Default for RSsystem {
|
||||||
|
fn default() -> Self {
|
||||||
|
RSsystem::new()
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
// -----------------------------------------------------------------------------
|
// -----------------------------------------------------------------------------
|
||||||
// RSsystem
|
// RSsystem
|
||||||
// -----------------------------------------------------------------------------
|
// -----------------------------------------------------------------------------
|
||||||
@ -361,9 +439,9 @@ pub struct RSlabel {
|
|||||||
pub context: RSset,
|
pub context: RSset,
|
||||||
pub t: RSset, /// union of available_entities and context
|
pub t: RSset, /// union of available_entities and context
|
||||||
pub reactants: RSset,
|
pub reactants: RSset,
|
||||||
pub reactantsi: RSset,
|
pub reactantsi: RSset, // reactants absent
|
||||||
pub inihibitors: RSset,
|
pub inihibitors: RSset,
|
||||||
pub ireactants: RSset,
|
pub ireactants: RSset, // inhibitors present
|
||||||
pub products: RSset,
|
pub products: RSset,
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -399,7 +477,7 @@ impl RSlabel {
|
|||||||
}
|
}
|
||||||
|
|
||||||
pub fn get_context(&self) -> (RSset, RSset, RSset) {
|
pub fn get_context(&self) -> (RSset, RSset, RSset) {
|
||||||
// FIXME clone?
|
// TODO remove clone?
|
||||||
(self.available_entities.clone(), self.context.clone(), self.t.clone())
|
(self.available_entities.clone(), self.context.clone(), self.t.clone())
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
@ -20,6 +20,12 @@ impl Translator {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
impl Default for Translator {
|
||||||
|
fn default() -> Self {
|
||||||
|
Translator::new()
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
impl Translator {
|
impl Translator {
|
||||||
pub fn encode(&mut self, s: impl Into<String>) -> IdType {
|
pub fn encode(&mut self, s: impl Into<String>) -> IdType {
|
||||||
let s = s.into();
|
let s = s.into();
|
||||||
@ -144,7 +150,7 @@ fn print_set(
|
|||||||
set: &RSset
|
set: &RSset
|
||||||
) -> fmt::Result {
|
) -> fmt::Result {
|
||||||
write!(f, "{{")?;
|
write!(f, "{{")?;
|
||||||
let mut it = set.hashset().iter().peekable();
|
let mut it = set.iter().peekable();
|
||||||
while let Some(el) = it.next() {
|
while let Some(el) = it.next() {
|
||||||
if it.peek().is_none() {
|
if it.peek().is_none() {
|
||||||
write!(f, "{}", translator.decode(*el))?;
|
write!(f, "{}", translator.decode(*el))?;
|
||||||
|
|||||||
25
testing/first.stats
Normal file
25
testing/first.stats
Normal file
@ -0,0 +1,25 @@
|
|||||||
|
Statistics:
|
||||||
|
=============================================================
|
||||||
|
the initial state has 2 entities:
|
||||||
|
{a, b}
|
||||||
|
The reactants are 2:
|
||||||
|
{a, b}
|
||||||
|
The inhibitors are 1:
|
||||||
|
{c}
|
||||||
|
The products are 1:
|
||||||
|
{b}
|
||||||
|
The reactions involve 3 entities:
|
||||||
|
{a, b, c}
|
||||||
|
The environment involves 2 entities:
|
||||||
|
{a, b}
|
||||||
|
The context involves 3 entities:
|
||||||
|
{a, b, c}
|
||||||
|
The whole RS involves 3 entities:
|
||||||
|
{a, b, c}
|
||||||
|
There are 0 reactants that will never be available:
|
||||||
|
{}
|
||||||
|
The context can provide 0 entities that will never be used:
|
||||||
|
{}
|
||||||
|
There are 1 reactions in total.
|
||||||
|
- the applicable reactions are 1.
|
||||||
|
- there are 0 reactions that will never be enabled.
|
||||||
4
testing/first.system
Normal file
4
testing/first.system
Normal file
@ -0,0 +1,4 @@
|
|||||||
|
Environment: [x = {a}.y, y =({a}.x + {b}.y)]
|
||||||
|
Initial Entities: {a, b}
|
||||||
|
Context: [({a,b}.{a}.{a,c}.x + {a,b}.{a}.{a}.nil)]
|
||||||
|
Reactions: ([r: {a,b}, i: {c}, p: {b}])
|
||||||
Reference in New Issue
Block a user