public final class MathExpr extends Object implements Function<Double[],Double>, Serializable
MathOp
.
final MathExpr expr = MathExpr.parse("5 + 6*x + sin(x)^34 + (1 + sin(x*5)/4)/6");
final double result = expr.eval(4.32);
assert result == 31.170600453465315;
assert 12.0 == MathExpr.eval("3*4");
assert 24.0 == MathExpr.eval("3*4*x", 2);
assert 28.0 == MathExpr.eval("3*4*x + y", 2, 4);
MathOp
,
Serialized FormModifier and Type | Field and Description |
---|---|
static TreeRewriter<Op<Double>> |
ARITHMETIC_REWRITER
This rewriter implements some common arithmetic identities, in exactly
this order.
|
static TreeRewriter<Op<Double>> |
CONST_REWRITER
This tree-rewriter rewrites constant expressions to its single value.
|
static TreeRewriter<Op<Double>> |
REWRITER
Combination of the
ARITHMETIC_REWRITER and the
CONST_REWRITER , in this specific order. |
Constructor and Description |
---|
MathExpr(Tree<? extends Op<Double>,?> tree)
Create a new
MathExpr object from the given operation tree. |
Modifier and Type | Method and Description |
---|---|
Double |
apply(Double[] args) |
boolean |
equals(Object obj) |
double |
eval(double... args)
Convenient method, which lets you apply the program function without
explicitly create a wrapper array.
|
static double |
eval(String expression,
double... args)
Evaluates the given
expression with the given arguments. |
static double |
eval(Tree<? extends Op<Double>,?> expression,
double... args)
Evaluates the given
expression with the given arguments. |
static String |
format(Tree<? extends Op<Double>,?> tree)
Return the string representation of the given
tree object. |
int |
hashCode() |
static MathExpr |
parse(String expression)
Parses the given
expression into a AST tree. |
static TreeNode<Op<Double>> |
parseTree(String expression)
Parses the given mathematical expression string and returns the
mathematical expression tree.
|
static int |
rewrite(TreeNode<Op<Double>> tree)
Applies the
REWRITER to the given (mutable) tree . |
static int |
rewrite(TreeNode<Op<Double>> tree,
int limit)
Applies the
REWRITER to the given (mutable) tree . |
MathExpr |
simplify()
Simplifies
this expression by applying the default
REWRITER . |
MathExpr |
simplify(TreeRewriter<Op<Double>> rewriter)
Simplifying
this expression by applying the given rewriter . |
MathExpr |
simplify(TreeRewriter<Op<Double>> rewriter,
int limit)
Simplifying
this expression by applying the given rewriter
and the given rewrite limit . |
String |
toString()
Return the string representation of this
MathExpr object. |
TreeNode<Op<Double>> |
toTree()
Return the math expression as operation tree.
|
ISeq<Var<Double>> |
vars()
Return the variable list of this math expression.
|
public static final TreeRewriter<Op<Double>> CONST_REWRITER
final TreeNode<Op<Double>> tree = MathExpr.parseTree("1 + 2*(6 + 7)");
MathExpr.CONST_REWRITER.rewrite(tree);
assertEquals(tree.getValue(), Const.of(27.0));
public static final TreeRewriter<Op<Double>> ARITHMETIC_REWRITER
sub($x,$x) -> 0
sub($x,0) -> $x
add($x,0) -> $x
add(0,$x) -> $x
add($x,$x) -> mul(2,$x)
div($x,$x) -> 1
div(0,$x) -> 0
mul($x,0) -> 0
mul(0,$x) -> 0
mul($x,1) -> $x
mul(1,$x) -> $x
mul($x,$x) -> pow($x,2)
pow($x,0) -> 1
pow(0,$x) -> 0
pow($x,1) -> $x
pow(1,$x) -> 1
public static final TreeRewriter<Op<Double>> REWRITER
ARITHMETIC_REWRITER
and the
CONST_REWRITER
, in this specific order.public MathExpr(Tree<? extends Op<Double>,?> tree)
MathExpr
object from the given operation tree.tree
- the underlying operation treeNullPointerException
- if the given program
is null
IllegalArgumentException
- if the given operation tree is invalid,
which means there is at least one node where the operation arity
and the node child count differ.public ISeq<Var<Double>> vars()
public TreeNode<Op<Double>> toTree()
public Double apply(Double[] args)
apply
in interface Function<Double[],Double>
eval(double...)
,
eval(String, double...)
public double eval(double... args)
final double result = MathExpr.parse("2*z + 3*x - y").eval(3, 2, 1);
assert result == 9.0;
args
- the function argumentsNullPointerException
- if the given variable array is null
IllegalArgumentException
- if the length of the arguments array
is smaller than the program arityapply(Double[])
,
eval(String, double...)
public String toString()
MathExpr
object. The
string returned by this method can be parsed again and will result in the
same expression object.
final String expr = "5.0 + 6.0*x + sin(x)^34.0 + (1.0 + sin(x*5.0)/4.0) + 6.5";
final MathExpr tree = MathExpr.parse(expr);
assert tree.toString().equals(expr);
public MathExpr simplify(TreeRewriter<Op<Double>> rewriter, int limit)
this
expression by applying the given rewriter
and the given rewrite limit
.rewriter
- the rewriter used for simplifying this
expressionlimit
- the rewrite limitNullPointerException
- if the rewriter
is null
IllegalArgumentException
- if the limit
is smaller than
zeropublic MathExpr simplify(TreeRewriter<Op<Double>> rewriter)
this
expression by applying the given rewriter
.rewriter
- the rewriter used for simplifying this
expressionNullPointerException
- if the rewriter
is null
public MathExpr simplify()
this
expression by applying the default
REWRITER
.public static String format(Tree<? extends Op<Double>,?> tree)
tree
object. The
string returned by this method can be parsed again and will result in the
same expression object.
final String expr = "5.0 + 6.0*x + sin(x)^34.0 + (1.0 + sin(x*5.0)/4.0) + 6.5";
final MathExpr tree = MathExpr.parse(expr);
assert MathExpr.format(tree.tree()).equals(expr);
tree
- the tree object to convert to a stringNullPointerException
- if the given tree
is null
public static MathExpr parse(String expression)
expression
into a AST tree.expression
- the expression stringexpression
NullPointerException
- if the given expression
is null
IllegalArgumentException
- if the given expression is invalid or
can't be parsed.public static TreeNode<Op<Double>> parseTree(String expression)
MathOp
.
final Tree<? extends Op<Double>, ?> tree = MathExpr
.parseTree("5 + 6*x + sin(x)^34 + (1 + sin(x*5)/4)/6");
add
├── add
│ ├── add
│ │ ├── 5.0
│ │ └── mul
│ │ ├── 6.0
│ │ └── x
│ └── pow
│ ├── sin
│ │ └── x
│ └── 34.0
└── div
├── add
│ ├── 1.0
│ └── div
│ ├── sin
│ │ └── mul
│ │ ├── x
│ │ └── 5.0
│ └── 4.0
└── 6.0
expression
- the expression stringNullPointerException
- if the given expression
is null
IllegalArgumentException
- if the given expression is invalid or
can't be parsed.public static double eval(String expression, double... args)
expression
with the given arguments.
final double result = MathExpr.eval("2*z + 3*x - y", 3, 2, 1);
assert result == 9.0;
expression
- the expression to evaluateargs
- the expression arguments, in alphabetical orderNullPointerException
- if the given expression
is
null
IllegalArgumentException
- if the given operation tree is invalid,
which means there is at least one node where the operation arity
and the node child count differ.apply(Double[])
,
eval(double...)
public static double eval(Tree<? extends Op<Double>,?> expression, double... args)
expression
with the given arguments.expression
- the expression to evaluateargs
- the expression arguments, in alphabetical orderNullPointerException
- if the given expression
is
null
apply(Double[])
,
eval(double...)
,
eval(String, double...)
public static int rewrite(TreeNode<Op<Double>> tree, int limit)
REWRITER
to the given (mutable) tree
. The
tree rewrite is done in place.tree
- the tree to be rewrittenlimit
- the maximal number this rewrite rule is applied to the given
tree. This guarantees the termination of the rewrite method.tree
NullPointerException
- if the given tree
is null
IllegalArgumentException
- if the limit
is smaller than
oneTreeRewriter.rewrite(TreeNode, int)
public static int rewrite(TreeNode<Op<Double>> tree)
REWRITER
to the given (mutable) tree
. The
tree rewrite is done in place. The limit of the applied rewrites is set
unlimited (Integer.MAX_VALUE
).tree
- the tree to be rewrittentrue
if the tree has been changed (rewritten) by this
method, false
if the tree hasn't been changedNullPointerException
- if the given tree
is null
rewrite(TreeNode, int)
,
TreeRewriter.rewrite(TreeNode)
© 2007-2019 Franz Wilhelmstötter (2019-11-18 20:30)