#! /usr/bin/env python # -*- coding: utf-8 -*- # vim:fenc=utf-8 # # Copyright © 2017 lafrite # # Distributed under terms of the MIT license. """ Tokens representing polynomials functions """ from ..expression import Expression from functools import partial from .token import Token from ...core.MO import MO from ...core.MO.atoms import moify __all__ = ["Polynomial", "Quadratic", "Linear"] class Polynomial(Token): """ Token representing a polynomial :examples: >>> from ...core.MO.polynomial import MOpolynomial >>> P = Polynomial(MOpolynomial('x', [1, 2, 3])) >>> P """ def __init__(self, a, name="", ancestor=None): if not isinstance(a, MO): if isinstance(a, str): raise TypeError else: raise TypeError else: mo = a Token.__init__(self, mo, name, ancestor) self._mathtype = "polynome" @classmethod def from_mo(cls, mo, name="", ancestor=None): return cls(mo, name, ancestor) @classmethod def random(cls): raise NotImplemented def __setitem__(self, key, item): """ Use Polynomial like if they were a dictionnary to set coefficients """ pass def __getitem__(self, key): """ Use Polynomial like if they were a dictionnary to get coefficients """ pass def __call__(self, value): """ Call a Polynomial to evaluate itself on value :examples: >>> from ...core.MO.polynomial import MOpolynomial >>> P = Polynomial(MOpolynomial('x', [1, 2, 3])) >>> for s in P(2).explain(): ... print(s) 3 * 2^2 + 2 * 2 + 1 3 * 4 + 4 + 1 12 + 5 17 """ tree = self._mo.tree variable = (set(tree.get_leafs(extract_variable)) - {None}).pop() dest = moify(value) replace_var = partial(replace, origin=variable, dest=dest) tree = tree.map_on_leaf(replace_var) return Expression(tree).simplify() class Linear(Polynomial): """ Token representing a linear """ def __init__(self, mo, name="", ancestor=None): Polynomial.__init__(self, mo, name, ancestor) self._mathtype = "affine" @classmethod def random(cls): raise NotImplemented class Quadratic(Polynomial): """ Token representing a quadratic """ def __init__(self, mo, name="", ancestor=None): Polynomial.__init__(self, mo, name, ancestor) self._mathtype = "polynome du 2nd degré" @classmethod def random(cls): raise NotImplemented def extract_variable(leaf): try: return leaf.variable except AttributeError: return None def replace(leaf, origin, dest): """ Recursively replace origin to dest in leaf """ try: leaf.tree except AttributeError: if leaf == origin: return dest return leaf replace_var = partial(replace, origin=origin, dest=dest) return leaf.tree.map_on_leaf(replace_var) # ----------------------------- # Reglages pour 'vim' # vim:set autoindent expandtab tabstop=4 shiftwidth=4: # cursor: 16 del