Closed terrorfisch closed 1 year ago
This is similar to #39. Can you give an example how you would want that to work syntactically as library user?
Let's the following method is added to FlatEx
/// EDITED: calls f with all variable names of self in the same order as self.var_names()
fn substituted<F>(&self, f: F) -> Self where F: FnMut(&str) -> Option<Self> {
todo!()
}
let some_expr = FlatEx::from_str("x*3+y/z")?;
// some other place in code
let substitutions: HashSet = [("x", FlatEx::from_str("a+b")?), ("z", FlatEx::from_str("3.4")?)].into_iter().collect();
let new_expression = some_expr.substituted(|name| subtitutions.get(name));
assert_eq!("(a+b)*3+y/3.4", new_expression.unparse()?)
Are you missing to loop over the HashSet
? Why does substituted have a callable as parameter instead of substituted(&self, name: &str, expr: Self) -> Self
?
I added a docstring to clarify the behaviour. I wanted to choose the form that imposes the least in the user. You can use it with a correctly ordered list of substitutions or with an aribtrary map.
One key property is that the substitutions are done at the same time.
let expr = "x/y".parse()?;
let substituted = expr.substituted(|name| {
match name {
"x" => Some("y".parse().unwrap()),
"y" => Some("x".parse().unwrap())
});
assert_eq!("y/x", substituted.unparse())
So in principle I want a rust equivalent to sympy's subs
Alternatively maybe something like:
fn subs<R: IntoIterator<Item=(&str, FlatEx)>>(&self, replacements: R) -> Result<Self> {
todo!()
}
Ah. Yeah. That looks interesting. I will think about how to implement this.
It would be nice to be able to substitute variables with arbitrary expressions.
My current workaround is to unparse, use
regex
replacement functionality and re-parse the expression.