From e8adef04b654cdb912a12d5b699a24960fd959dc Mon Sep 17 00:00:00 2001 From: Matt Wala <wala1@illinois.edu> Date: Mon, 21 Jan 2019 18:50:34 -0600 Subject: [PATCH] Round 1 of changes --- pymbolic/geometric_algebra/mapper.py | 9 ++++++- pymbolic/imperative/transform.py | 2 +- pymbolic/interop/ast.py | 6 ++++- pymbolic/interop/common.py | 7 +++++ pymbolic/interop/sympy.py | 2 +- pymbolic/mapper/__init__.py | 21 +++++++++++++++ pymbolic/mapper/constant_folder.py | 2 +- pymbolic/mapper/differentiator.py | 2 +- pymbolic/mapper/unifier.py | 3 +++ pymbolic/parser.py | 2 +- pymbolic/polynomial.py | 40 +++++++++++----------------- pymbolic/primitives.py | 16 +++++++++-- 12 files changed, 78 insertions(+), 34 deletions(-) diff --git a/pymbolic/geometric_algebra/mapper.py b/pymbolic/geometric_algebra/mapper.py index 448d408..5ee9326 100644 --- a/pymbolic/geometric_algebra/mapper.py +++ b/pymbolic/geometric_algebra/mapper.py @@ -145,11 +145,15 @@ class Dimensionalizer(EvaluationMapper): Dimension of ambient space. Must be provided by subclass. """ + @property + def ambient_dim(self): + raise NotImplementedError + def map_multivector_variable(self, expr): from pymbolic.primitives import make_sym_vector return MultiVector( make_sym_vector(expr.name, self.ambient_dim, - var_class=type(expr))) + var_factory=type(expr))) def map_nabla(self, expr): from pytools.obj_array import make_obj_array @@ -232,6 +236,9 @@ class DerivativeBinder(IdentityMapper): self.derivative_source_and_nabla_component_collector() self.restrict_to_id = restrict_to_id + def take_derivative(self, ambient_axis, expr): + raise NotImplementedError + def map_product(self, expr): # {{{ gather NablaComponents and DerivativeSources diff --git a/pymbolic/imperative/transform.py b/pymbolic/imperative/transform.py index b324bab..6f4c08d 100644 --- a/pymbolic/imperative/transform.py +++ b/pymbolic/imperative/transform.py @@ -67,7 +67,7 @@ def fuse_instruction_streams_with_unique_ids(insns_a, insns_b): def disambiguate_identifiers(statements_a, statements_b, should_disambiguate_name=None): if should_disambiguate_name is None: - def should_disambiguate_name(name): + def should_disambiguate_name(name): # pylint:disable=function-redefined return True from pymbolic.imperative.analysis import get_all_used_identifiers diff --git a/pymbolic/interop/ast.py b/pymbolic/interop/ast.py index 6a826f1..d7787b8 100644 --- a/pymbolic/interop/ast.py +++ b/pymbolic/interop/ast.py @@ -91,12 +91,15 @@ class ASTMapper(object): # {{{ mapper class ASTToPymbolic(ASTMapper): + @staticmethod def _add(x, y): # noqa return p.Sum((x, y)) + @staticmethod def _sub(x, y): # noqa return p.Sum((x, p.Product(((-1), y)))) + @staticmethod def _mult(x, y): # noqa return p.Product((x, y)) @@ -127,8 +130,9 @@ class ASTToPymbolic(ASTMapper): return op_constructor(self.rec(expr.left), self.rec(expr.right)) + @staticmethod def _neg(x): # noqa - return p.Product((-1), x) + return p.Product((-1, x),) unary_op_map = { ast.Invert: _neg, diff --git a/pymbolic/interop/common.py b/pymbolic/interop/common.py index d8b75f5..23ea2ea 100644 --- a/pymbolic/interop/common.py +++ b/pymbolic/interop/common.py @@ -130,6 +130,13 @@ class SympyLikeToPymbolicMapper(SympyLikeMapperBase): class PymbolicToSympyLikeMapper(EvaluationMapper): + @property + def sym(self): + raise NotImplementedError + + def raise_conversion_error(self, message): + raise NotImplementedError + def map_variable(self, expr): return self.sym.Symbol(expr.name) diff --git a/pymbolic/interop/sympy.py b/pymbolic/interop/sympy.py index 1e31ead..76ef76c 100644 --- a/pymbolic/interop/sympy.py +++ b/pymbolic/interop/sympy.py @@ -61,7 +61,7 @@ class SympyToPymbolicMapper(SympyLikeToPymbolicMapper): # only called for Py2 def map_long(self, expr): - return long(expr) # noqa + return long(expr) # noqa pylint:disable=undefined-variable def map_Indexed(self, expr): # noqa return prim.Subscript( diff --git a/pymbolic/mapper/__init__.py b/pymbolic/mapper/__init__.py index a280d51..3ed5240 100644 --- a/pymbolic/mapper/__init__.py +++ b/pymbolic/mapper/__init__.py @@ -135,6 +135,9 @@ class Mapper(object): rec = __call__ + def map_algebraic_leaf(self, expr, *args, **kwargs): + raise NotImplementedError + def map_variable(self, expr, *args, **kwargs): return self.map_algebraic_leaf(expr, *args, **kwargs) @@ -153,6 +156,21 @@ class Mapper(object): def map_rational(self, expr, *args, **kwargs): return self.map_quotient(expr, *args, **kwargs) + def map_quotient(self, expr, *args, **kwargs): + raise NotImplementedError + + def map_constant(self, expr, *args, **kwargs): + raise NotImplementedError + + def map_list(self, expr, *args, **kwargs): + raise NotImplementedError + + def map_tuple(self, expr, *args, **kwargs): + raise NotImplementedError + + def map_numpy_array(self, expr, *args, **kwargs): + raise NotImplementedError + def map_foreign(self, expr, *args, **kwargs): """Mapper method dispatch for non-:mod:`pymbolic` objects.""" @@ -195,6 +213,9 @@ class CombineMapper(RecursiveMapper): :class:`pymbolic.mapper.dependency.DependencyMapper` is another example. """ + def combine(self, values): + raise NotImplementedError + def map_call(self, expr, *args, **kwargs): return self.combine( (self.rec(expr.function, *args, **kwargs),) diff --git a/pymbolic/mapper/constant_folder.py b/pymbolic/mapper/constant_folder.py index b642fa6..f40e4ad 100644 --- a/pymbolic/mapper/constant_folder.py +++ b/pymbolic/mapper/constant_folder.py @@ -47,7 +47,7 @@ class ConstantFoldingMapperBase(object): queue = list(expr.children) while queue: - child = self.rec(queue.pop(0)) + child = self.rec(queue.pop(0)) # pylint:disable=no-member if isinstance(child, klass): queue = list(child.children) + queue else: diff --git a/pymbolic/mapper/differentiator.py b/pymbolic/mapper/differentiator.py index 86ac2f9..b6ec695 100644 --- a/pymbolic/mapper/differentiator.py +++ b/pymbolic/mapper/differentiator.py @@ -174,7 +174,7 @@ class DifferentiationMapper(pymbolic.mapper.RecursiveMapper): return ( Polynomial(self.rec_undiff(expr.base, *args), - tuple(deriv_coeff), expr.unit) + + tuple(deriv_coeff), expr.unit) + Polynomial(self.rec_undiff(expr.base, *args), tuple(deriv_base), expr.unit)) diff --git a/pymbolic/mapper/unifier.py b/pymbolic/mapper/unifier.py index aa1f825..4ac8f2c 100644 --- a/pymbolic/mapper/unifier.py +++ b/pymbolic/mapper/unifier.py @@ -119,6 +119,9 @@ class UnifierBase(RecursiveMapper): self.rhs_mapping_candidates = rhs_mapping_candidates self.force_var_match = force_var_match + def treat_mismatch(self, expr, other, urecs): + raise NotImplementedError + def unification_record_from_equation(self, lhs, rhs): if isinstance(lhs, (tuple, list)) or isinstance(rhs, (tuple, list)): # Always force lists/tuples to agree elementwise, never diff --git a/pymbolic/parser.py b/pymbolic/parser.py index 00ef94a..8f199b3 100644 --- a/pymbolic/parser.py +++ b/pymbolic/parser.py @@ -212,7 +212,7 @@ class Parser(object): left_exp = self.parse_expression(pstate, _PREC_UNARY) elif pstate.is_next(_minus): pstate.advance() - left_exp = -self.parse_expression(pstate, _PREC_UNARY) + left_exp = -self.parse_expression(pstate, _PREC_UNARY) # noqa pylint:disable=invalid-unary-operand-type elif pstate.is_next(_not): pstate.advance() from pymbolic.primitives import LogicalNot diff --git a/pymbolic/polynomial.py b/pymbolic/polynomial.py index ad878fd..bcb04e2 100644 --- a/pymbolic/polynomial.py +++ b/pymbolic/polynomial.py @@ -56,6 +56,13 @@ def _sort_uniq(data): +def _get_dependencies(expr): + from pymbolic.mapper.dependency import DependencyMapper + return DependencyMapper()(expr) + + + + class LexicalMonomialOrder: def __call__(self, a, b): from pymbolic.primitives import Variable @@ -70,9 +77,6 @@ class LexicalMonomialOrder: return "LexicalMonomialOrder()" - - - class Polynomial(Expression): def __init__(self, base, data=None, unit=1, var_less=LexicalMonomialOrder()): self.Base = base @@ -218,7 +222,7 @@ class Polynomial(Expression): return quot * self, rem * self if other.degree == -1: - raise DivisionByZeroError + raise ZeroDivisionError quot = Polynomial(self.Base, ()) rem = self @@ -252,11 +256,11 @@ class Polynomial(Expression): __truediv__ = __div__ - def __floordiv__(self): - return self.__divmod__(self, other)[0] + def __floordiv__(self, other): + return self.__divmod__(other)[0] - def __mod__(self): - return self.__divmod__(self, other)[1] + def __mod__(self, other): + return self.__divmod__(other)[1] def _data(self): return self.Data @@ -283,7 +287,7 @@ class Polynomial(Expression): mapper_method = intern("map_polynomial") def as_primitives(self): - deps = pymbolic.get_dependencies(self) + deps = _get_dependencies(self) context = dict((dep, dep) for dep in deps) return pymbolic.evaluate(self, context) @@ -297,21 +301,6 @@ class Polynomial(Expression): -def from_primitives(expr, var_order): - from pymbolic import get_dependencies, evaluate - - deps = get_dependencies(expr) - var_deps = [dep for dep in deps if dep in var_order] - context = dict((vd, Polynomial(vd, var_order=var_order)) - for vd in var_deps) - - # FIXME not fast, but works - # (and exercises multivariate polynomial code) - return evaluate(expr, context) - - - - def differentiate(poly): return Polynomial( poly.base, @@ -335,7 +324,8 @@ def integrate_definite(poly, a, b): a_bound = pymbolic.substitute(antideriv, {poly.base: a}) b_bound = pymbolic.substitute(antideriv, {poly.base: b}) - return pymbolic.sum((b_bound, -a_bound)) + from pymbolic.primitives import Sum + return Sum((b_bound, -a_bound)) diff --git a/pymbolic/primitives.py b/pymbolic/primitives.py index d18c1c6..d6198e3 100644 --- a/pymbolic/primitives.py +++ b/pymbolic/primitives.py @@ -216,6 +216,14 @@ class Expression(object): .. automethod:: ge """ + # {{{ init arg names (override by subclass) + + @property + def init_arg_names(self): + raise NotImplementedError + + # }}} + # {{{ arithmetic def __add__(self, other): @@ -516,6 +524,9 @@ class Expression(object): self.hash_value = self.get_hash() return self.hash_value + def __getinitargs__(self): + raise NotImplementedError + def __getstate__(self): return self.__getinitargs__() @@ -1297,8 +1308,9 @@ class Vector(Expression): return Vector(tuple(other*x for x in self)) def __div__(self, other): + # Py2 only import operator - return Vector(tuple(operator.div(x, other) for x in self)) + return Vector(tuple(operator.div(x, other) for x in self)) # pylint: disable=no-member def __truediv__(self, other): import operator @@ -1557,7 +1569,7 @@ global VALID_CONSTANT_CLASSES global VALID_OPERANDS VALID_CONSTANT_CLASSES = (int, float, complex) if six.PY2: - VALID_CONSTANT_CLASSES += (long,) # noqa + VALID_CONSTANT_CLASSES += (long,) # noqa pylint:disable=undefined-variable VALID_OPERANDS = (Expression,) -- GitLab