From d9e6f0981b2eddba894736d71fa91e71b05b9519 Mon Sep 17 00:00:00 2001 From: elvis Date: Mon, 19 May 2025 00:10:23 +0200 Subject: [PATCH] Simple process reaction --- src/main.rs | 28 ++++-- src/rsprocess/classical.rs | 13 +++ src/rsprocess/grammar.lalrpop | 50 ++++++---- src/rsprocess/mod.rs | 105 +------------------- src/rsprocess/structure.rs | 174 ++++++++++++++++++++++++++++++++++ 5 files changed, 241 insertions(+), 129 deletions(-) create mode 100644 src/rsprocess/classical.rs create mode 100644 src/rsprocess/structure.rs diff --git a/src/main.rs b/src/main.rs index 009287a..3e07f37 100644 --- a/src/main.rs +++ b/src/main.rs @@ -1,16 +1,32 @@ mod rsprocess; use lalrpop_util::lalrpop_mod; -use std::io; +// use std::io; fn main() -> Result<(), Box> { lalrpop_mod!(grammar, "/rsprocess/grammar.rs"); - let mut buffer = String::new(); - let i = io::stdin(); - i.read_line(&mut buffer).expect("Can't read stdin"); + // let mut buffer = String::new(); + // let i = io::stdin(); + // i.read_line(&mut buffer).expect("Can't read stdin"); - let result = grammar::BHMLParser::new().parse(&buffer).unwrap(); - println!("{:?}", result); + // let result = grammar::SetParser::new().parse(&buffer).unwrap(); + + + let reactants = grammar::SetParser::new().parse("{a}").unwrap(); + let inihibitors = grammar::SetParser::new().parse("{c}").unwrap(); + let products = grammar::SetParser::new().parse("{a,c}").unwrap(); + + let process1 = rsprocess::structure::RSreaction::from(reactants, inihibitors, products); + + let reactants = grammar::SetParser::new().parse("{b}").unwrap(); + let inihibitors = grammar::SetParser::new().parse("{c}").unwrap(); + let products = grammar::SetParser::new().parse("{b,c}").unwrap(); + + let process2 = rsprocess::structure::RSreaction::from(reactants, inihibitors, products); + + let current_state = grammar::SetParser::new().parse("{b}").unwrap(); + + println!("{:?}", rsprocess::classical::compute_all(¤t_state, vec![&process1, &process2])); Ok(()) } diff --git a/src/rsprocess/classical.rs b/src/rsprocess/classical.rs new file mode 100644 index 0000000..bc3fb3b --- /dev/null +++ b/src/rsprocess/classical.rs @@ -0,0 +1,13 @@ +use super::structure::{RSset, RSreaction}; + +pub fn compute_step<'a>(current_state: &RSset<'a>, reaction: &RSreaction<'a>) -> RSset<'a> { + if reaction.enabled(current_state) { + reaction.products_clone() + } else { + RSset::new() + } +} + +pub fn compute_all<'a>(current_state: &RSset<'a>, reactions: Vec<&RSreaction<'a>>) -> RSset<'a> { + reactions.iter().fold(RSset::new(), |acc, r| acc.union(&compute_step(current_state, r))) +} diff --git a/src/rsprocess/grammar.lalrpop b/src/rsprocess/grammar.lalrpop index 928631b..2e28bf0 100644 --- a/src/rsprocess/grammar.lalrpop +++ b/src/rsprocess/grammar.lalrpop @@ -1,6 +1,6 @@ use std::str::FromStr; use lalrpop_util::ParseError; -use crate::rsprocess::{RSset, RSprocess, RSenvironment, RSassert, RSassertOp, RSBHML}; +use crate::rsprocess::structure::{RSset, RSprocess, RSenvironment, RSassert, RSassertOp, RSBHML}; grammar; @@ -29,28 +29,35 @@ pub Set: RSset<'input> = { => s }; -// ----- ContextParser ----- -pub Context: Box> = { - "[" "]" => Box::new(RSprocess::Nill), - "[" "]" => Box::new(t), - "[" > "]" => Box::new(RSprocess::NondeterministicChoice{children: t}) -}; - -CTX_process: RSprocess<'input> = { - "." => RSprocess::EntitySet{entities: c, next_process: Box::new(k)}, - "(" ")" => k, - "(" > ")" => RSprocess::Summation{children: k}, - "<" ">" "." => RSprocess::WaitEntity{repeat: n, repeated_process: Box::new(k1), next_process: Box::new(k)}, - "nil" => RSprocess::Nill, - => RSprocess::ConstantIdentifier{identifier: identifier} -}; - Set_of_entities: RSset<'input> = { "{" "}" => RSset::from(vec![]), "{" "}" => RSset::from(vec![t]), "{" > "}" => RSset::from(t) }; +// ----- ContextParser ----- +pub Context: Box> = { + "[" "]" => Box::new(RSprocess::Nill), + "[" "]" => Box::new(t), + "[" > "]" => + Box::new(RSprocess::NondeterministicChoice{ children: t }) +}; + +CTX_process: RSprocess<'input> = { + "." => + RSprocess::EntitySet{ entities: c, next_process: Box::new(k) }, + "(" ")" => k, + "(" > ")" => + RSprocess::Summation{ children: k }, + "<" ">" "." => + RSprocess::WaitEntity{ repeat: n, + repeated_process: Box::new(k1), + next_process: Box::new(k)}, + "nil" => RSprocess::Nill, + => + RSprocess::ConstantIdentifier{ identifier: identifier } +}; + // ----- EnvironmentParser ----- pub Environment: Box> = { "[" "]" => Box::new(RSenvironment::new()), @@ -68,7 +75,8 @@ pub Assert: Box> = { Formula_Assert: RSassert<'input> = { "-" => RSassert::Not(Box::new(f)), - "(" "^" ")" => RSassert::Xor(Box::new(f1), Box::new(f2)), + "(" "^" ")" => + RSassert::Xor(Box::new(f1), Box::new(f2)), "(" > ")" => RSassert::Or(f), "(" > ")" => RSassert::And(f), "inW" => RSassert::Sub(c, RSassertOp::InW), @@ -91,6 +99,8 @@ Formula_BHML: RSBHML<'input> = { "false" => RSBHML::False, "(" > ")" => RSBHML::Or(g), "(" > ")" => RSBHML::And(g), - "<" ">" => RSBHML::Diamond(Box::new(f), Box::new(g)), - "[" "]" => RSBHML::Box(Box::new(f), Box::new(g)), + "<" ">" => + RSBHML::Diamond(Box::new(f), Box::new(g)), + "[" "]" => + RSBHML::Box(Box::new(f), Box::new(g)), }; diff --git a/src/rsprocess/mod.rs b/src/rsprocess/mod.rs index 5348efa..79a78c9 100644 --- a/src/rsprocess/mod.rs +++ b/src/rsprocess/mod.rs @@ -1,103 +1,2 @@ -use std::collections::BTreeMap; - -#[derive(Clone, Debug)] -#[allow(dead_code)] -pub struct RSset<'a> { - identifiers: Vec<&'a str> -} - -impl<'a, const N: usize> From<[&'a str; N]> for RSset<'a> { - fn from(mut arr: [&'a str; N]) -> Self { - arr.sort(); - RSset{identifiers: arr.to_vec()} - } -} - -impl<'a> From<&[&'a str]> for RSset<'a> { - fn from(arr: &[&'a str]) -> Self { - let mut tmp = arr.to_vec(); - tmp.sort(); - RSset{identifiers: tmp} - } -} - -impl<'a> From> for RSset<'a> { - fn from(mut arr: Vec<&'a str>) -> Self { - arr.sort(); - RSset{identifiers: arr} - } -} - - -#[derive(Clone, Debug)] -#[allow(dead_code)] -pub enum RSprocess<'a> { - Nill, - ConstantIdentifier{identifier: &'a str}, - EntitySet{entities: RSset<'a>, next_process: Box>}, - WaitEntity{repeat: i64, repeated_process: Box>, next_process: Box>}, - NondeterministicChoice{children: Vec>}, - Summation{children: Vec>} -} - -#[derive(Clone, Debug)] -#[allow(dead_code)] -pub struct RSenvironment<'a> { - definitions: BTreeMap<&'a str, Box>>, -} - -impl<'a> RSenvironment<'a> { - pub fn new() -> RSenvironment<'a> { - RSenvironment{definitions: BTreeMap::new()} - } -} - -impl<'a, const N: usize> From<[(&'a str, Box>); N]> for RSenvironment<'a> { - fn from(arr: [(&'a str, Box>); N]) -> Self { - RSenvironment{definitions: BTreeMap::from(arr)} - } -} - -impl<'a> From<&[(&'a str, Box>)]> for RSenvironment<'a> { - fn from(arr: &[(&'a str, Box>)]) -> Self { - RSenvironment{definitions: BTreeMap::from_iter(arr.to_vec())} - } -} - -impl<'a> From>)>> for RSenvironment<'a> { - fn from(arr: Vec<(&'a str, Box>)>) -> Self { - RSenvironment{definitions: BTreeMap::from_iter(arr)} - } -} - -#[derive(Clone, Debug)] -#[allow(dead_code)] -pub enum RSassertOp { - InW, - InR, - InI, - InP -} - - -#[derive(Clone, Debug)] -#[allow(dead_code)] -pub enum RSassert<'a> { - Not(Box>), - Xor(Box>, Box>), - Or(Vec>), - And(Vec>), - Sub(RSset<'a>, RSassertOp), - NonEmpty(RSassertOp) -} - -#[derive(Clone, Debug)] -#[allow(dead_code)] -pub enum RSBHML<'a> { - True, - False, - Or(Vec>), - And(Vec>), - Diamond(Box>, Box>), - Box(Box>, Box>) -} +pub mod structure; +pub mod classical; diff --git a/src/rsprocess/structure.rs b/src/rsprocess/structure.rs new file mode 100644 index 0000000..3d0247f --- /dev/null +++ b/src/rsprocess/structure.rs @@ -0,0 +1,174 @@ +use std::collections::{BTreeMap, HashSet}; + +// ----------------------------------------------------------------------------- +// RSset +// ----------------------------------------------------------------------------- +#[derive(Clone, Debug)] +#[allow(dead_code)] +pub struct RSset<'a> { + identifiers: HashSet<&'a str> +} + +impl<'a, const N: usize> From<[&'a str; N]> for RSset<'a> { + fn from(arr: [&'a str; N]) -> Self { + RSset{identifiers: HashSet::from(arr)} + } +} + +impl<'a> From<&[&'a str]> for RSset<'a> { + fn from(arr: &[&'a str]) -> Self { + RSset{identifiers: HashSet::from_iter(arr.to_vec())} + } +} + +impl<'a> From> for RSset<'a> { + fn from(arr: Vec<&'a str>) -> Self { + RSset{identifiers: HashSet::from_iter(arr)} + } +} + +impl<'a> RSset<'a> { + pub fn new() -> Self { + RSset{identifiers: HashSet::new()} + } + + pub fn is_subset(&self, b: &RSset<'a>) -> bool { + self.identifiers.is_subset(&b.identifiers) + } + + pub fn is_disjoint(&self, b: &RSset<'a>) -> bool { + self.identifiers.is_disjoint(&b.identifiers) + } + + pub fn union(&self, b: &RSset<'a>) -> RSset<'a> { + // TODO maybe find more efficient way + let mut ret: RSset = b.clone(); + ret.identifiers.extend(self.identifiers.iter()); + ret + } +} + + +// ----------------------------------------------------------------------------- +// RSreaction +// ----------------------------------------------------------------------------- +#[derive(Clone, Debug)] +#[allow(dead_code)] +pub struct RSreaction<'a> { + reactants: RSset<'a>, + inihibitors: RSset<'a>, + products: RSset<'a> +} + +impl<'a> RSreaction<'a> { + pub fn new() -> Self { + RSreaction{ reactants: RSset::new(), + inihibitors: RSset::new(), + products: RSset::new(), } + } + + pub fn from(reactants: RSset<'a>, inihibitors: RSset<'a>, products: RSset<'a>) -> Self { + RSreaction{ reactants, + inihibitors, + products } + } + + pub fn enabled(&self, current_state: &RSset<'a>) -> bool { + self.reactants.is_subset(current_state) + && self.inihibitors.is_disjoint(current_state) + } + + pub fn products_clone(&self) -> RSset<'a> { + self.products.clone() + } +} + + + +// ----------------------------------------------------------------------------- +// RSprocess +// ----------------------------------------------------------------------------- +#[derive(Clone, Debug)] +#[allow(dead_code)] +pub enum RSprocess<'a> { + Nill, + ConstantIdentifier{identifier: &'a str}, + EntitySet{entities: RSset<'a>, next_process: Box>}, + WaitEntity{repeat: i64, repeated_process: Box>, next_process: Box>}, + NondeterministicChoice{children: Vec>}, + Summation{children: Vec>} +} + + +// ----------------------------------------------------------------------------- +// RSenvironment +// ----------------------------------------------------------------------------- +#[derive(Clone, Debug)] +#[allow(dead_code)] +pub struct RSenvironment<'a> { + definitions: BTreeMap<&'a str, Box>>, +} + +impl<'a> RSenvironment<'a> { + pub fn new() -> RSenvironment<'a> { + RSenvironment{definitions: BTreeMap::new()} + } +} + +impl<'a, const N: usize> From<[(&'a str, Box>); N]> for RSenvironment<'a> { + fn from(arr: [(&'a str, Box>); N]) -> Self { + RSenvironment{definitions: BTreeMap::from(arr)} + } +} + +impl<'a> From<&[(&'a str, Box>)]> for RSenvironment<'a> { + fn from(arr: &[(&'a str, Box>)]) -> Self { + RSenvironment{definitions: BTreeMap::from_iter(arr.to_vec())} + } +} + +impl<'a> From>)>> for RSenvironment<'a> { + fn from(arr: Vec<(&'a str, Box>)>) -> Self { + RSenvironment{definitions: BTreeMap::from_iter(arr)} + } +} + +// ----------------------------------------------------------------------------- +// RSassertOp +// ----------------------------------------------------------------------------- +#[derive(Clone, Debug)] +#[allow(dead_code)] +pub enum RSassertOp { + InW, + InR, + InI, + InP +} + +// ----------------------------------------------------------------------------- +// RSassert +// ----------------------------------------------------------------------------- +#[derive(Clone, Debug)] +#[allow(dead_code)] +pub enum RSassert<'a> { + Not(Box>), + Xor(Box>, Box>), + Or(Vec>), + And(Vec>), + Sub(RSset<'a>, RSassertOp), + NonEmpty(RSassertOp) +} + +// ----------------------------------------------------------------------------- +// RSBHML +// ----------------------------------------------------------------------------- +#[derive(Clone, Debug)] +#[allow(dead_code)] +pub enum RSBHML<'a> { + True, + False, + Or(Vec>), + And(Vec>), + Diamond(Box>, Box>), + Box(Box>, Box>) +}