Use multipledispatch to define divide (plus dostring for add)

This commit is contained in:
Bertrand Benjamin 2018-03-17 10:38:59 +03:00
parent c08ea7b86a
commit f4422c6d1a
2 changed files with 49 additions and 76 deletions

View File

@ -10,19 +10,19 @@
Adding MO Adding MO
""" """
from multipledispatch import Dispatcher
from ..tree import Tree from ..tree import Tree
from ..MO.mo import MO, MOnumber from ..MO.mo import MO, MOnumber
from ..MO.fraction import MOFraction from ..MO.fraction import MOFraction
from .exceptions import AddError from .exceptions import AddError
from .arithmetic import lcm from .arithmetic import lcm
from .type_filter import args_are from .type_filter import args_are
from multipledispatch import Dispatcher
add_doc = """ Adding MOs add_doc = """ Adding MOs
:param left: left MO :param left: left MO
:param right: right MO :param right: right MO
:return: Tree or MO :return: Tree or MO
""" """
add = Dispatcher("add", doc=add_doc) add = Dispatcher("add", doc=add_doc)

View File

@ -10,51 +10,26 @@
Divide MO Divide MO
""" """
from multipledispatch import Dispatcher
from ..tree import Tree from ..tree import Tree
from ..MO.mo import MO, MOnumber from ..MO.mo import MO, MOnumber
from ..MO.fraction import MOFraction from ..MO.fraction import MOFraction
from .exceptions import DivideError from .exceptions import DivideError
from .type_filter import args_are from .type_filter import args_are
divide_doc = """ Dividing MOs
def divide(left, right): :param left: left MO
""" Perform the addition of left and right :param right: right MO
:returns: Tree or MO
:param left: left MO """
:param right: right MO
:returns: Tree or MO
>>> a = MOnumber(4) divide = Dispatcher("divide", doc=divide_doc)
>>> b = MOnumber(6)
>>> divide(a, b)
<MOFraction 4 / 6>
>>> b = MOnumber(0)
>>> divide(a, b)
Traceback (most recent call last):
...
mapytex.calculus.core.compute.exceptions.DivideError: Division by zero
""" @divide.register(MOnumber, MOnumber)
try:
right.value
except AttributeError:
pass
else:
if right.value == 0:
raise DivideError("Division by zero")
if right.value == 1:
return left
return MULFUNCTIONS[(type(left), type(right))](left, right)
@args_are(MOnumber, MOnumber)
def monumber_monumber(left, right): def monumber_monumber(left, right):
""" Divide 2 monumbers """ Divide 2 monumbers and return a MOFraction
:param left: left MOnumber
:param right: right MOnumber
:returns: MONumber
>>> a = MOnumber(4) >>> a = MOnumber(4)
>>> b = MOnumber(6) >>> b = MOnumber(6)
@ -63,13 +38,9 @@ def monumber_monumber(left, right):
""" """
return MOFraction(left, right) return MOFraction(left, right)
@args_are(MOnumber, MOFraction) @divide.register(MOnumber, MOFraction)
def monumber_mofraction(left, right): def monumber_mofraction(left, right):
""" Divide a monumber and a mofraction """ Divide a monumber and a mofraction by inverting MOFraction
:param left: a monumber
:param right: a mofraction
:returns: Tree with the multiplication on the numerator
>>> a = MOnumber(4) >>> a = MOnumber(4)
>>> b = MOFraction(6, 5) >>> b = MOFraction(6, 5)
@ -89,19 +60,11 @@ def monumber_mofraction(left, right):
| | > 5 | | > 5
| | > 6 | | > 6
""" """
if not isinstance(left, MOnumber) or not isinstance(right, MOFraction):
raise DivideError(f"Wrong type for left (got {left.__class__.__name__}) \
or right (got {right.__class__.__name__})")
return Tree("*", left, right.inverse()) return Tree("*", left, right.inverse())
@args_are(MOFraction, MOnumber) @divide.register(MOFraction, MOnumber)
def mofraction_monumber(left, right): def mofraction_monumber(left, right):
""" Divide a monumber and a mofraction """ Divide a monumber and a mofraction by inverting MOnumber
:param left: a mofraction
:param right: a monumber
:returns: Tree with a new calculus
>>> a = MOFraction(6, 5) >>> a = MOFraction(6, 5)
>>> b = MOnumber(4) >>> b = MOnumber(4)
@ -115,20 +78,12 @@ def mofraction_monumber(left, right):
| > 4 | > 4
""" """
if not isinstance(left, MOFraction) or not isinstance(right, MOnumber):
raise DivideError(f"Wrong type for left (got {left.__class__.__name__})"
f"or right (got {right.__class__.__name__})")
right_fraction = MOFraction(1, right) right_fraction = MOFraction(1, right)
return Tree("*", left, right_fraction) return Tree("*", left, right_fraction)
@args_are(MOFraction, MOFraction) @divide.register(MOFraction, MOFraction)
def mofraction_mofraction(left, right): def mofraction_mofraction(left, right):
""" Divide two mofractions """ Divide two mofractions by inverting right MOFraction
:param left: a mofraction
:param right: a mofraction
:returns: Tree with a new calculus
>>> a = MOFraction(1, 5) >>> a = MOFraction(1, 5)
>>> b = MOFraction(4, 5) >>> b = MOFraction(4, 5)
@ -142,20 +97,38 @@ def mofraction_mofraction(left, right):
| > 4 | > 4
""" """
if not isinstance(left, MOFraction) or not isinstance(right, MOFraction):
raise AddError(f"Wrong type for left (got {left.__class__.__name__})"
f"or right (got {right.__class__.__name__})")
return Tree("*", left, right.inverse()) return Tree("*", left, right.inverse())
# TODO: Faire un décorateur pour un enregistrement automatique |dim. mars 11 18:24:32 EAT 2018 #def divide(left, right):
MULFUNCTIONS = { # """ Perform the addition of left and right
(MOnumber, MOnumber): monumber_monumber, #
(MOnumber, MOFraction): monumber_mofraction, # :param left: left MO
(MOFraction, MOnumber): mofraction_monumber, # :param right: right MO
(MOFraction, MOFraction): mofraction_mofraction, # :returns: Tree or MO
} #
# >>> a = MOnumber(4)
# >>> b = MOnumber(6)
# >>> divide(a, b)
# <MOFraction 4 / 6>
# >>> b = MOnumber(0)
# >>> divide(a, b)
# Traceback (most recent call last):
# ...
# mapytex.calculus.core.compute.exceptions.DivideError: Division by zero
#
# """
# try:
# right.value
# except AttributeError:
# pass
# else:
# if right.value == 0:
# raise DivideError("Division by zero")
#
# if right.value == 1:
# return left
#
# return MULFUNCTIONS[(type(left), type(right))](left, right)
# ----------------------------- # -----------------------------
# Reglages pour 'vim' # Reglages pour 'vim'