Fix(API): Rewrite tree apply_on_last_level and reorganise simplify

This commit is contained in:
Bertrand Benjamin 2018-11-19 12:23:37 +01:00
parent 6edf4fe5b4
commit e37a8a5a2e
4 changed files with 67 additions and 29 deletions

View File

@ -21,6 +21,7 @@ Generate and compute like a student!
2 + 12
14
>>> e = Expression.from_str("2+3/2")
>>> e_simplified = e.simplify()
>>> print(e_simplified)
@ -34,6 +35,20 @@ Generate and compute like a student!
(4 + 3) / 2
7 / 2
>>> e = Expression.from_str("(2+3)/2 + 1")
>>> e_simplified = e.simplify()
>>> print(e_simplified)
7 / 2
>>> for s in e_simplified.explain():
... print(s)
(2 + 3) / 2 + 1
5 / 2 + 1
5 / 2 + 1 / 1
5 / 2 + (1 * 2) / (1 * 2)
5 / 2 + 2 / 2
(5 + 2) / 2
7 / 2
>>> e = Expression.from_str("(2/3)^4")
>>> e_simplified = e.simplify()
>>> print(e_simplified)
@ -54,10 +69,28 @@ x^2 * x * x^4
x^3 * x^4
x^(3 + 4)
x^7
>>> e = Expression.from_str("2x+2+3x")
>>> e_simplified = e.simplify()
>>> print(e_simplified)
5x + 2
>>> for s in e_simplified.explain():
... print(s)
2x + 2 + 3x
2x + 3x + 2
(2 + 3) * x + 2
5x + 2
"""
from .expression import Expression
if __name__ == "__main__":
e = Expression.from_str("2x+2+3x")
print(e)
e_simplified = e.simplify()
print(e_simplified)
# -----------------------------
# Reglages pour 'vim'

View File

@ -10,7 +10,7 @@
Expression
"""
from ..core import AssocialTree, Tree, compute, typing
from ..core import AssocialTree, Tree, compute, typing, TypingError
from .renders import renders
class Expression(object):
@ -104,20 +104,31 @@ class Expression(object):
>>> f._ancestor
<Exp: 2 + 12>
"""
t = self._tree
if optimize:
try:
# TODO: need to test exclude_nodes |ven. oct. 5 08:51:02 CEST 2018
self._tree = self._tree.balance(
t = t.balance(
exclude_nodes=["\\", "**"]
)
except AttributeError:
pass
more_typing = 1
while more_typing:
try:
t = t.apply_on_last_level(typing)
except TypingError:
more_typing = 0
except NotImplementedError:
more_typing = 0
except AttributeError:
more_typing = 0
try:
t = self._tree.apply_on_last_level(compute, typing)
t = t.apply_on_last_level(compute)
except AttributeError:
return self
except NotImplementedError:
return self
else:
e = Expression(t, ancestor=self)
return e.simplify(optimize=optimize)

View File

@ -18,7 +18,7 @@ Abstracts tools for calculs manipulations
> *
| > 3
| > 4
>>> print(t.apply_on_last_level(compute, typing))
>>> print(t.apply_on_last_level(compute))
+
> 2
> 12
@ -34,7 +34,12 @@ Abstracts tools for calculs manipulations
> /
| > 3
| > 4
>>> print(t.apply_on_last_level(compute, typing))
>>> print(t.apply_on_last_level(compute))
Traceback (most recent call last):
...
NotImplementedError: Can't divide 2 int. Need to create a Fraction instead
>>> tt = t.apply_on_last_level(typing)
>>> print(tt.apply_on_last_level(compute))
+
> /
| > 2
@ -42,7 +47,12 @@ Abstracts tools for calculs manipulations
> /
| > 3
| > 4
>>> type(t.right_value)
<class 'mapytex.calculus.core.tree.Tree'>
>>> type(tt.right_value)
<class 'mapytex.calculus.core.MO.fraction.MOFraction'>
>>> tt.right_value
<MOFraction 3 / 4>
>>> t = Tree.from_str("2+3x")
>>> print(t)
@ -56,7 +66,7 @@ Abstracts tools for calculs manipulations
from .tree import Tree, AssocialTree
from .compute import compute
from .typing import typing
from .typing import typing, TypingError
from .renders import tree2txt, tree2tex

View File

@ -294,13 +294,10 @@ class Tree(object):
return Tree(self.node, left_applied, right_applied)
def apply_on_last_level(self,
function,
fallback = lambda n,l,r: Tree(n,l,r)):
def apply_on_last_level(self, function):
""" Apply the function on last level of the tree before leaf
:param function: (op, a, a) -> b function to apply on last level
:param fallback: (op, a, a) -> b fallback function to apply on subtree which raise a NotImplementedError. The return value will be concidered as an leaf
:returns: b if it is a 1 level Tree, Tree otherwise
@ -330,30 +327,17 @@ class Tree(object):
"""
left_is_leaf = 0
right_is_leaf = 0
try:
left_applied = self.left_value.\
apply_on_last_level(function, fallback)
except NotImplementedError:
# TODO: overload __getitem__ to ease unpacking |dim. sept. 23 19:17:50 CEST 2018
left_is_leaf = 1
left_tree = self.left_value
left_applied = fallback(left_tree.node,
left_tree.left_value,
left_tree.right_value)
apply_on_last_level(function)
except AttributeError:
left_applied = self.left_value
left_is_leaf = 1
right_is_leaf = 0
try:
right_applied = self.right_value.\
apply_on_last_level(function, fallback)
except NotImplementedError:
right_is_leaf = 1
right_tree = self.right_value
right_applied = fallback(right_tree.node,
right_tree.left_value,
right_tree.right_value)
apply_on_last_level(function)
except AttributeError:
right_applied = self.right_value
right_is_leaf = 1