Reduce and print poly ok!
This commit is contained in:
		| @@ -41,15 +41,15 @@ class Expression(object): | |||||||
|     ## --------------------- |     ## --------------------- | ||||||
|     ## Mechanism functions |     ## Mechanism functions | ||||||
|  |  | ||||||
|     def simplify(self): |     def simplify(self, render=STR_RENDER): | ||||||
|         """ Generator which return steps for computing the expression  """ |         """ Generator which return steps for computing the expression  """ | ||||||
|         if not self.can_go_further(): |         if not self.can_go_further(): | ||||||
|             yield self.STR_RENDER(self.postfix_tokens)  |             yield render(self.postfix_tokens)  | ||||||
|         else: |         else: | ||||||
|             self.compute_exp()  |             self.compute_exp()  | ||||||
|             old_s = '' |             old_s = '' | ||||||
|             for s in self.steps: |             for s in self.steps: | ||||||
|                 new_s = self.STR_RENDER(s) |                 new_s = render(s) | ||||||
|                 # Astuce pour éviter d'avoir deux fois la même étape (par exemple pour la transfo d'une division en fraction) |                 # Astuce pour éviter d'avoir deux fois la même étape (par exemple pour la transfo d'une division en fraction) | ||||||
|                 if new_s != old_s: |                 if new_s != old_s: | ||||||
|                     old_s = new_s |                     old_s = new_s | ||||||
|   | |||||||
| @@ -264,7 +264,23 @@ def spe_zip(l1,l2): | |||||||
|         ans.append(j) |         ans.append(j) | ||||||
|     return ans |     return ans | ||||||
|  |  | ||||||
|  | def transpose_fill(list_lists): | ||||||
|  |     """Transpose a list of list and if inside list have not the same length, fill with last token | ||||||
|  |      | ||||||
|  |     :list_lists: a list of list to transpose | ||||||
|  |     :returns: generator which generate lines of the transposed matrix | ||||||
|  |  | ||||||
|  |     >>> Polynom.transpose_fill([[1], [2, 3], [4, 5, 6]]) | ||||||
|  |     [[1, 2, 4] , [1, 3, 5], [1, 3, 6]] | ||||||
|  |     """ | ||||||
|  |     for i in range(max([len(l) for l in list_lists])): | ||||||
|  |         col = [] | ||||||
|  |         for l in list_lists: | ||||||
|  |             try: | ||||||
|  |                 col.append(l[i]) | ||||||
|  |             except IndexError: | ||||||
|  |                 col.append(l[-1]) | ||||||
|  |         yield col | ||||||
|  |  | ||||||
| def isOperator(exp): | def isOperator(exp): | ||||||
|     """Check if the expression is an opération in "+-*/:^" |     """Check if the expression is an opération in "+-*/:^" | ||||||
|   | |||||||
| @@ -3,8 +3,11 @@ | |||||||
|  |  | ||||||
|  |  | ||||||
| from .expression import Expression | from .expression import Expression | ||||||
| from .generic import spe_zip, sum_postfix, expand_list, isNumber | from .operator import op | ||||||
|  | from .generic import spe_zip, expand_list, isNumber, transpose_fill, flatten_list | ||||||
|  | #from .generic import spe_zip, sum_postfix, expand_list, isNumber | ||||||
| from .render import txt | from .render import txt | ||||||
|  | from itertools import chain | ||||||
|  |  | ||||||
| __all__ = ["Polynom"] | __all__ = ["Polynom"] | ||||||
|  |  | ||||||
| @@ -23,6 +26,14 @@ class Polynom(object): | |||||||
|                 - a: a Expression. [1, Expression("2+3"), 4] designate 1 + (2+3)x + 4x^2 |                 - a: a Expression. [1, Expression("2+3"), 4] designate 1 + (2+3)x + 4x^2 | ||||||
|         :param letter: the string describing the unknown |         :param letter: the string describing the unknown | ||||||
|  |  | ||||||
|  |         >>> Polynom([1,2,3]).mainOp | ||||||
|  |         '+' | ||||||
|  |         >>> Polynom([1]).mainOp | ||||||
|  |         '*' | ||||||
|  |         >>> Polynom([1,2, 3])._letter | ||||||
|  |         'x' | ||||||
|  |         >>> Polynom([1, 2, 3], "y")._letter | ||||||
|  |         'y' | ||||||
|         """ |         """ | ||||||
|         self.feed_coef(coef) |         self.feed_coef(coef) | ||||||
|         self._letter = letter |         self._letter = letter | ||||||
| @@ -33,7 +44,7 @@ class Polynom(object): | |||||||
|         else: |         else: | ||||||
|             self.mainOp = "+" |             self.mainOp = "+" | ||||||
|  |  | ||||||
|         self._isPolynom |         self._isPolynom = 1 | ||||||
|  |  | ||||||
|     def feed_coef(self, l_coef): |     def feed_coef(self, l_coef): | ||||||
|         """Feed coef of the polynom. Manage differently whether it's a number or an expression |         """Feed coef of the polynom. Manage differently whether it's a number or an expression | ||||||
| @@ -52,12 +63,22 @@ class Polynom(object): | |||||||
|  |  | ||||||
|         :returns: the degree of the polynom |         :returns: the degree of the polynom | ||||||
|  |  | ||||||
|  |         >>> Polynom([1, 2, 3]).get_degree() | ||||||
|  |         2 | ||||||
|  |         >>> Polynom([1]).get_degree() | ||||||
|  |         0 | ||||||
|         """ |         """ | ||||||
|         return len(self._coef) - 1 |         return len(self._coef) - 1 | ||||||
|  |  | ||||||
|     def is_monom(self): |     def is_monom(self): | ||||||
|         """is the polynom a monom (only one coefficent) |         """is the polynom a monom (only one coefficent) | ||||||
|  |  | ||||||
|         :returns: 1 if yes 0 otherwise |         :returns: 1 if yes 0 otherwise | ||||||
|  |  | ||||||
|  |         >>> Polynom([1, 2, 3]).is_monom() | ||||||
|  |         0 | ||||||
|  |         >>> Polynom([1]).is_monom() | ||||||
|  |         1 | ||||||
|         """ |         """ | ||||||
|         if len([i for i in self._coef if i != 0])==1: |         if len([i for i in self._coef if i != 0])==1: | ||||||
|             return 1 |             return 1 | ||||||
| @@ -65,8 +86,7 @@ class Polynom(object): | |||||||
|             return 0 |             return 0 | ||||||
|  |  | ||||||
|     def __str__(self): |     def __str__(self): | ||||||
|         # TODO: Voir si on peut utiliser un render |sam. juin 14 08:56:16 CEST 2014 |         return txt(self.postfix) | ||||||
|         return txt(self.get_postfix()) |  | ||||||
|  |  | ||||||
|     def __repr__(self): |     def __repr__(self): | ||||||
|         return  "< Polynom " + str(self._coef) + ">" |         return  "< Polynom " + str(self._coef) + ">" | ||||||
| @@ -74,7 +94,7 @@ class Polynom(object): | |||||||
|     def coef_postfix(self, a, i): |     def coef_postfix(self, a, i): | ||||||
|         """Return the postfix display of a coeficient |         """Return the postfix display of a coeficient | ||||||
|  |  | ||||||
|         :param a: value for the coeficient (/!\ as a list) |         :param a: value for the coeficient (/!\ as a postfix list) | ||||||
|         :param i: power |         :param i: power | ||||||
|         :returns: postfix tokens of coef |         :returns: postfix tokens of coef | ||||||
|  |  | ||||||
| @@ -86,46 +106,34 @@ class Polynom(object): | |||||||
|         if i == 0: |         if i == 0: | ||||||
|             ans = a |             ans = a | ||||||
|         elif i == 1: |         elif i == 1: | ||||||
|             ans = a * (a!=[1]) + [self._letter] + ["*"] *  (a!=[1])  |             ans = a * (a!=[1]) + [self._letter] + [op.mul] *  (a!=[1])  | ||||||
|         else: |         else: | ||||||
|             ans = a * (a!=[1]) + [self._letter, i, "^"] + ["*"] *  (a!=[1])  |             ans = a * (a!=[1]) + [self._letter, i, op.pw] + [op.mul] *  (a!=[1])  | ||||||
|  |  | ||||||
|         return ans |         return ans | ||||||
|  |  | ||||||
|     def get_postfix(self): |     @property | ||||||
|  |     def postfix(self): | ||||||
|         """Return the postfix form of the polynom |         """Return the postfix form of the polynom | ||||||
|  |  | ||||||
|         :returns: the postfix list of polynom's tokens |         :returns: the postfix list of polynom's tokens | ||||||
|  |  | ||||||
|         """ |         """ | ||||||
|         self._postfix = [] |         postfix = [] | ||||||
|         first_elem = 1 |  | ||||||
|         for (i,a) in list(enumerate(self._coef))[::-1]: |         for (i,a) in list(enumerate(self._coef))[::-1]: | ||||||
|             if type(a) == list and str(a[-1]) in "+-*^/": |             if type(a) == Expression: | ||||||
|                 # case coef is an arithmetic expression |                 # case coef is an arithmetic expression | ||||||
|                 self._postfix += self.coef_postfix(a,i) |                 postfix.append(self.coef_postfix(a.postfix_tokens,i)) | ||||||
|                 if not first_elem: |  | ||||||
|                     self._postfix.append("+") |  | ||||||
|                 first_elem = 0 |  | ||||||
|  |  | ||||||
|             elif type(a) == list and str(a[-1]) not in "+-*^/": |             elif type(a) == list: | ||||||
|                 # case need to repeat the x^i |                 # case need to repeat the x^i | ||||||
|                 for b in a: |                 for b in a: | ||||||
|                     if type(b) == list: |                     postfix.append(self.coef_postfix([b],i)) | ||||||
|                         self._postfix += self.coef_postfix(b,i) |  | ||||||
|                     else: |  | ||||||
|                         self._postfix += self.coef_postfix([b],i) |  | ||||||
|                     if not first_elem: |  | ||||||
|                         self._postfix.append("+") |  | ||||||
|                     first_elem = 0 |  | ||||||
|  |  | ||||||
|             elif a != 0: |             elif a != 0: | ||||||
|                 self._postfix += self.coef_postfix([a],i) |                     postfix.append(self.coef_postfix([a],i)) | ||||||
|                 if not first_elem: |  | ||||||
|                     self._postfix.append("+") |  | ||||||
|                 first_elem = 0 |  | ||||||
|  |  | ||||||
|         return self._postfix |         return flatten_list(self.postfix_add(postfix)) | ||||||
|  |  | ||||||
|     def conv2poly(self, other): |     def conv2poly(self, other): | ||||||
|         """Convert anything number into a polynom""" |         """Convert anything number into a polynom""" | ||||||
| @@ -149,53 +157,54 @@ class Polynom(object): | |||||||
|         :returns: new Polynom with numbers coefficients |         :returns: new Polynom with numbers coefficients | ||||||
|         """ |         """ | ||||||
|         steps = [] |         steps = [] | ||||||
|         for a in self._coef: |         # gather steps for every coeficients | ||||||
|  |         coefs_steps = [] | ||||||
|  |         for coef in self._coef: | ||||||
|             coef_steps = [] |             coef_steps = [] | ||||||
|             if type(a) == Expression: |             if type(coef) != Expression: | ||||||
|                 # case coef is an arithmetic expression |                 # On converti en postfix avec une addition | ||||||
|                 coef_steps = list(a.simplify(render = lambda x:x)) |                 postfix_add = self.postfix_add(coef) | ||||||
|                  |                 # On converti en Expression | ||||||
|                 steps.append(coef_steps) |                 coef_exp = Expression(postfix_add) | ||||||
|             elif type(a) == list: |  | ||||||
|                 # case need to repeat the x^i |  | ||||||
|                 if [i for i in a if type(i) == list] != []: |  | ||||||
|                     # first we simplify arithmetic exp |  | ||||||
|                     # Et hop un coup de sorcelerie! |  | ||||||
|                     elem = [list(Expression(i).simplify(render = lambda x:self.list_or_num(x))) if type(i) == list else i for i in a ] |  | ||||||
|  |  | ||||||
|                     elem = expand_list(elem) |  | ||||||
|                     coef_steps += elem |  | ||||||
|                     exp = elem[-1] |  | ||||||
|  |  | ||||||
|                 else: |  | ||||||
|                     exp = a |  | ||||||
|  |  | ||||||
|                 exp = sum_postfix(exp) |  | ||||||
|                 exp = Expression(exp) |  | ||||||
|                  |  | ||||||
|                 coef_steps += list(exp.simplify(render = lambda x:x)) |  | ||||||
|                  |  | ||||||
|                 steps.append(coef_steps) |  | ||||||
|             else: |             else: | ||||||
|                 steps.append(a) |                 coef_exp = coef | ||||||
|  |  | ||||||
|         steps = expand_list(steps) |             # On fait réduire l'expression puis on ajoute dans steps | ||||||
|          |             coef_steps = list(coef_exp.simplify(render = lambda x:Expression(x))) | ||||||
|         return [Polynom(s) for s in steps] |  | ||||||
|  |             # On ajoute toutes ces étapes | ||||||
|  |             coefs_steps.append(coef_steps) | ||||||
|  |  | ||||||
|  |         # On retourne la matrice | ||||||
|  |         for coefs in transpose_fill(coefs_steps): | ||||||
|  |             yield Polynom(coefs, self._letter) | ||||||
|  |  | ||||||
|     @staticmethod |     @staticmethod | ||||||
|     def list_or_num(x): |     def postfix_add(numbers): | ||||||
|         if len(x) == 1: |         """Convert a list of numbers into a postfix addition | ||||||
|             return x[0] |          | ||||||
|  |         :numbers: list of numbers | ||||||
|  |         :returns: Postfix list of succecive attition of number | ||||||
|  |  | ||||||
|  |         >>> Polynom.postfix_add([1]) | ||||||
|  |         [1] | ||||||
|  |         >>> Polynom.postfix_add([1, 2]) | ||||||
|  |         [1, 2, '+'] | ||||||
|  |         >>> Polynom.postfix_add([1, 2, 3]) | ||||||
|  |         [1, 2, '+', 3, '+'] | ||||||
|  |         >>> Polynom.postfix_add(1) | ||||||
|  |         [1] | ||||||
|  |         """ | ||||||
|  |         if not type(numbers) == list: | ||||||
|  |             return [numbers] | ||||||
|         else: |         else: | ||||||
|             return x |             ans = [[a, op.add] if i!=0 else [a] for (i,a) in enumerate(numbers)] | ||||||
|  |             return list(chain.from_iterable(ans)) | ||||||
|  |              | ||||||
|     def simplify(self): |     def simplify(self): | ||||||
|         """Same as reduce """ |         """Same as reduce """ | ||||||
|         return self.reduce() |         return self.reduce() | ||||||
|  |  | ||||||
|  |  | ||||||
|     def __eq__(self, other): |     def __eq__(self, other): | ||||||
|         o_poly = self.conv2poly(other) |         o_poly = self.conv2poly(other) | ||||||
|         return self._coef == o_poly._coef |         return self._coef == o_poly._coef | ||||||
| @@ -275,23 +284,24 @@ def test(p,q): | |||||||
|     print("\n Plus ------") |     print("\n Plus ------") | ||||||
|     for i in (p + q): |     for i in (p + q): | ||||||
|         #print(repr(i)) |         #print(repr(i)) | ||||||
|         #print("\t", str(i.get_postfix())) |         #print("\t", str(i.postfix)) | ||||||
|         print(i) |         print(i) | ||||||
|  |  | ||||||
|     print("\n Moins ------") |     print("\n Moins ------") | ||||||
|     for i in (p - q): |     for i in (p - q): | ||||||
|         #print(repr(i)) |         #print(repr(i)) | ||||||
|         #print("\t", str(i.get_postfix())) |         #print("\t", str(i.postfix)) | ||||||
|         print(i) |         print(i) | ||||||
|  |  | ||||||
|     print("\n Multiplier ------") |     print("\n Multiplier ------") | ||||||
|     for i in (p * q): |     for i in (p * q): | ||||||
|         #print(repr(i)) |         #print(repr(i)) | ||||||
|         #print("\t", str(i.get_postfix())) |         #print("\t", str(i.postfix)) | ||||||
|         print(i) |         print(i) | ||||||
|      |      | ||||||
|  |  | ||||||
| if __name__ == '__main__': | if __name__ == '__main__': | ||||||
|  |     from .fraction import Fraction | ||||||
|     p = Polynom([1, -2 ]) |     p = Polynom([1, -2 ]) | ||||||
|     q = Polynom([4, 7]) |     q = Polynom([4, 7]) | ||||||
|     #test(p,q) |     #test(p,q) | ||||||
| @@ -304,10 +314,10 @@ if __name__ == '__main__': | |||||||
|  |  | ||||||
|  |  | ||||||
|     #print("-- Poly étrange --") |     #print("-- Poly étrange --") | ||||||
|     #p = Polynom([1, [[2, 3, "*"],3], 4], "x") |     p = Polynom([1, [2, 3], 4], "x") | ||||||
|     #print(repr(p)) |     print(repr(p)) | ||||||
|     #for i in p.simplify(): |     for i in p.simplify(): | ||||||
|     #    print(repr(i)) |         print(i) | ||||||
|     #print("-- Poly étrange --") |     #print("-- Poly étrange --") | ||||||
|     #p = Polynom([1, [[2, 3, "*"], [4,5,"*"]], 4], "x") |     #p = Polynom([1, [[2, 3, "*"], [4,5,"*"]], 4], "x") | ||||||
|     #print(repr(p)) |     #print(repr(p)) | ||||||
| @@ -315,6 +325,9 @@ if __name__ == '__main__': | |||||||
|     #for i in p.simplify(): |     #for i in p.simplify(): | ||||||
|     #    print(repr(i)) |     #    print(repr(i)) | ||||||
|  |  | ||||||
|  |     import doctest | ||||||
|  |     doctest.testmod() | ||||||
|  |  | ||||||
|  |  | ||||||
| # ----------------------------- | # ----------------------------- | ||||||
| # Reglages pour 'vim' | # Reglages pour 'vim' | ||||||
|   | |||||||
		Reference in New Issue
	
	Block a user