From 219037e87a5eae1fb0ddb5298251b6d51a618e20 Mon Sep 17 00:00:00 2001 From: Benjamin Bertrand Date: Thu, 10 Mar 2016 14:42:27 +0300 Subject: [PATCH] introduce Step remove pstf_factory in Expression --- pymath/calculus/expression.py | 153 +++++++++++++++++----------------- pymath/calculus/step.py | 68 +++++++++++++++ 2 files changed, 145 insertions(+), 76 deletions(-) create mode 100644 pymath/calculus/step.py diff --git a/pymath/calculus/expression.py b/pymath/calculus/expression.py index 840f3af..7601901 100644 --- a/pymath/calculus/expression.py +++ b/pymath/calculus/expression.py @@ -8,6 +8,7 @@ from .generic import flatten_list, expand_list, isOperator, isNumerand from .str2tokens import str2tokens from .operator import op from .explicable import Explicable, Explicable_int, Explicable_Decimal +from .step import Step from decimal import Decimal from .random_expression import RdExpression @@ -15,41 +16,41 @@ from .random_expression import RdExpression __all__ = ['Expression'] -def pstf_factory(pstf_tokens): - """Factory which tranform postfix tokens list into an Expression or the simpliest object type ready to be rendered - - :param pstf_tokens: a postfix tokens list - :returns: the object - - >>> from .operator import op - >>> pstf_t = [2, 3, op.add] - >>> pstf_factory(pstf_t) - < Expression [2, 3, +]> - >>> pstf_factory([2]) - 2 - >>> type(pstf_factory([2])) - - >>> pstf_factory([2.45]) - Decimal('2.45') - >>> type(pstf_factory([2.45])) - - >>> from .fraction import Fraction - >>> f = Fraction(1,2) - >>> pstf_factory([f]) - < Fraction 1 / 2> - - """ - if len(pstf_tokens) == 1: - if isinstance(pstf_tokens[0], int): - return Explicable_int(pstf_tokens[0]) - elif isinstance(pstf_tokens[0], Decimal): - return Explicable_Decimal(pstf_tokens[0]) - elif isinstance(pstf_tokens[0], float): - return Explicable_Decimal(Decimal(str(pstf_tokens[0]))) - elif hasattr(pstf_tokens[0], 'STR_RENDER'): - return pstf_tokens[0] - - return Expression(pstf_tokens) +# def pstf_factory(pstf_tokens): +# """Factory which tranform postfix tokens list into an Expression or the simpliest object type ready to be rendered +# +# :param pstf_tokens: a postfix tokens list +# :returns: the object +# +# >>> from .operator import op +# >>> pstf_t = [2, 3, op.add] +# >>> pstf_factory(pstf_t) +# < Expression [2, 3, +]> +# >>> pstf_factory([2]) +# 2 +# >>> type(pstf_factory([2])) +# +# >>> pstf_factory([2.45]) +# Decimal('2.45') +# >>> type(pstf_factory([2.45])) +# +# >>> from .fraction import Fraction +# >>> f = Fraction(1,2) +# >>> pstf_factory([f]) +# < Fraction 1 / 2> +# +# """ +# if len(pstf_tokens) == 1: +# if isinstance(pstf_tokens[0], int): +# return Explicable_int(pstf_tokens[0]) +# elif isinstance(pstf_tokens[0], Decimal): +# return Explicable_Decimal(pstf_tokens[0]) +# elif isinstance(pstf_tokens[0], float): +# return Explicable_Decimal(Decimal(str(pstf_tokens[0]))) +# elif hasattr(pstf_tokens[0], 'STR_RENDER'): +# return pstf_tokens[0] +# +# return Expression(pstf_tokens) class Expression(Explicable): @@ -68,44 +69,44 @@ class Expression(Explicable): random_generator = RdExpression(form, conditions) return Expression(random_generator(val_min, val_max)) - @classmethod - def tmp_render(cls, render=lambda _, x: pstf_factory(x)): - """ Same ad tmp_render for Renderable but default render is Expression + # @classmethod + # def tmp_render(cls, render=lambda _, x: pstf_factory(x)): + # """ Same ad tmp_render for Renderable but default render is Expression - >>> exp = Expression("2*3/5") - >>> print(exp) - 2 \\times \\frac{ 3 }{ 5 } - >>> for i in exp.simplify().explain(): - ... print(i) - 2 \\times \\frac{ 3 }{ 5 } - \\frac{ 3 }{ 5 } \\times 2 - \\frac{ 3 \\times 2 }{ 5 } - \\frac{ 6 }{ 5 } - >>> with Expression.tmp_render(): - ... for i in exp.simplify().explain(): - ... i - < Expression [2, 3, 5, /, *]> - < Expression [2, < Fraction 3 / 5>, *]> - < Expression [< Fraction 3 / 5>, 2, *]> - < Expression [3, 2, *, 5, /]> - < Expression [6, 5, /]> - >>> from .render import txt - >>> with Expression.tmp_render(txt): - ... for i in exp.simplify().explain(): - ... print(i) - 2 * 3 / 5 - 3 / 5 * 2 - ( 3 * 2 ) / 5 - 6 / 5 - >>> for i in exp.simplify().explain(): - ... print(i) - 2 \\times \\frac{ 3 }{ 5 } - \\frac{ 3 }{ 5 } \\times 2 - \\frac{ 3 \\times 2 }{ 5 } - \\frac{ 6 }{ 5 } + # >>> exp = Expression("2*3/5") + # >>> print(exp) + # 2 \\times \\frac{ 3 }{ 5 } + # >>> for i in exp.simplify().explain(): + # ... print(i) + # 2 \\times \\frac{ 3 }{ 5 } + # \\frac{ 3 }{ 5 } \\times 2 + # \\frac{ 3 \\times 2 }{ 5 } + # \\frac{ 6 }{ 5 } + # >>> with Expression.tmp_render(): + # ... for i in exp.simplify().explain(): + # ... i + # < Expression [2, 3, 5, /, *]> + # < Expression [2, < Fraction 3 / 5>, *]> + # < Expression [< Fraction 3 / 5>, 2, *]> + # < Expression [3, 2, *, 5, /]> + # < Expression [6, 5, /]> + # >>> from .render import txt + # >>> with Expression.tmp_render(txt): + # ... for i in exp.simplify().explain(): + # ... print(i) + # 2 * 3 / 5 + # 3 / 5 * 2 + # ( 3 * 2 ) / 5 + # 6 / 5 + # >>> for i in exp.simplify().explain(): + # ... print(i) + # 2 \\times \\frac{ 3 }{ 5 } + # \\frac{ 3 }{ 5 } \\times 2 + # \\frac{ 3 \\times 2 }{ 5 } + # \\frac{ 6 }{ 5 } - """ - return super(Expression, cls).tmp_render(render) + # """ + # return super(Expression, cls).tmp_render(render) def __init__(self, exp): """Create Expression objects @@ -261,7 +262,7 @@ class Expression(Explicable): >>> f = Expression('3*4+5') >>> f1 = f.simplify() >>> Expression.develop_steps([e1, f1, op.add]) - [< Expression [1, 2, +, 3, 4, *, 5, +, +]>, < Expression [3, 12, 5, +, +]>] + [< Step [1, 2, +, 3, 4, *, 5, +, +]>, < Step [3, 12, 5, +, +]>, < Step [3, 17, +]>] >>> e = Expression('1+2') >>> e1 = e.simplify() >>> f = Expression('3*4+5') @@ -269,13 +270,13 @@ class Expression(Explicable): >>> g = Expression('6+7') >>> g1 = g.simplify() >>> Expression.develop_steps([e1, f1, op.add, g1, op.mul]) - [< Expression [1, 2, +, 3, 4, *, 5, +, +, 6, 7, +, *]>, < Expression [3, 12, 5, +, +, 13, *]>] + [< Step [1, 2, +, 3, 4, *, 5, +, +, 6, 7, +, *]>, < Step [3, 12, 5, +, +, 13, *]>, < Step [3, 17, +, 13, *]>] """ - with Expression.tmp_render(): + with Step.tmp_render(): tmp_steps = list(Explicable.merge_history(tokenList)) - tmp_steps = list(tmp_steps)[:-1] - steps = [Expression(s) for s in tmp_steps] + tmp_steps = list(tmp_steps) + steps = [Step(s) for s in tmp_steps] return steps @classmethod diff --git a/pymath/calculus/step.py b/pymath/calculus/step.py new file mode 100644 index 0000000..5b48418 --- /dev/null +++ b/pymath/calculus/step.py @@ -0,0 +1,68 @@ +#!/usr/bin/env python +# encoding: utf-8 + +from .renderable import Renderable + +__all__ = ['Step'] + +class Step(Renderable): + """ + A step is a Renderable which his only goal is to be render. + """ + + @classmethod + def tmp_render(cls): + """ Create a container in which the method explain return only Step object. + + >>> from .expression import Expression + >>> exp = Expression("2*3/5") + >>> print(exp) + 2 \\times \\frac{ 3 }{ 5 } + >>> for i in exp.simplify().explain(): + ... print(i) + 2 \\times \\frac{ 3 }{ 5 } + \\frac{ 3 }{ 5 } \\times 2 + \\frac{ 3 \\times 2 }{ 5 } + \\frac{ 6 }{ 5 } + >>> with Step.tmp_render(): + ... for i in exp.simplify().explain(): + ... print(i) + < Step [2, 3, 5, /, *]> + < Step [3, 5, /, 2, *]> + < Step [3, 2, *, 5, /]> + < Step [6, 5, /]> + >>> for i in exp.simplify().explain(): + ... print(i) + 2 \\times \\frac{ 3 }{ 5 } + \\frac{ 3 }{ 5 } \\times 2 + \\frac{ 3 \\times 2 }{ 5 } + \\frac{ 6 }{ 5 } + + """ + return super(Step, cls).tmp_render(Step) + + def __init__(self, pstf_tokens): + """Initiate the renderable objet + + :param pstf_tokens: the postfix list of tokens + + >>> s = Step([2, 3, '+']) + >>> s + < Step [2, 3, '+']> + >>> s1 = Step([s, 5, '*']) + >>> s1 + < Step [2, 3, '+', 5, '*']> + + """ + self.postfix_tokens = [] + for t in pstf_tokens: + try: + self.postfix_tokens += t.postfix_tokens + except AttributeError: + self.postfix_tokens.append(t) + + +# ----------------------------- +# Reglages pour 'vim' +# vim:set autoindent expandtab tabstop=4 shiftwidth=4: +# cursor: 16 del