UnevaluateExpr is still somewhat experimental. It looks like passing
evaluate=False to the Piecewise does the trick.

However, this could be considered a bug. How does it result in bigger
and bigger expressions with the folding?

Aaron Meurer
On Wed, Oct 3, 2018 at 8:50 PM Nathaniel Virgo <[email protected]> wrote:
>
>
> When constructing a sympy.PIecewise object, it automatically calls 
> piecewise_fold if it finds a Piecewise inside a condition. I would like to 
> prevent this, because I’m using sympy for code generation and this 
> auto-expansion is causing my expressions to explode exponentially.
>
>
> Here is a simple example of this auto-substituion:
>
>
> >>> import sympy as sym
>
> >>> x = sym.Symbol(‘x’)
>
> >>> y =  sym.Piecewise((0,x<0),(x,True))
>
> >>> sym.Piecewise((y,y<1),(1,True))
>
> Piecewise((Piecewise((0, x < 0), (x, True)), x < 1), (1, True))
>
>
> Note that the reference to y in the condition y<1 has been removed by the 
> auto-folding. This is what I’m trying to prevent, because in my case it 
> results in bigger and bigger expressions. Unfortunately this doesn’t work:
>
>
> >>> sym.piecewise_fold(sym.Piecewise((y,sym.UnevaluatedExpr(y<1)),(1,True)))
>
> Traceback (most recent call last):
>
>   File "<stdin>", line 1, in <module>
>
>   File 
> "/Users/ndv/Library/Python/3.6/lib/python/site-packages/sympy/functions/elementary/piecewise.py",
>  line 129, in __new__
>
>     pair = ExprCondPair(*getattr(ec, 'args', ec))
>
>   File 
> "/Users/ndv/Library/Python/3.6/lib/python/site-packages/sympy/functions/elementary/piecewise.py",
>  line 31, in __new__
>
>     cond = cond.rewrite(ITE)
>
>   File 
> "/Users/ndv/Library/Python/3.6/lib/python/site-packages/sympy/core/basic.py", 
> line 1681, in rewrite
>
>     return self._eval_rewrite(None, rule, **hints)
>
>   File 
> "/Users/ndv/Library/Python/3.6/lib/python/site-packages/sympy/core/basic.py", 
> line 1589, in _eval_rewrite
>
>     rewritten = getattr(self, rule)(*args)
>
>   File 
> "/Users/ndv/Library/Python/3.6/lib/python/site-packages/sympy/functions/elementary/piecewise.py",
>  line 916, in _eval_rewrite_as_ITE
>
>     ''' % func_name(b)))
>
> TypeError:
>
> Expecting Boolean or bool but got `UnevaluatedExpr`
>
>
> And neither does this, which gives a fairly spectacular stack trace:
>
> >>> sym.piecewise_fold(sym.Piecewise((y,sym.UnevaluatedExpr(y)<1),(1,True)))
>
> Traceback (most recent call last):
>
>   File "<stdin>", line 1, in <module>
>
>   File 
> "/Users/ndv/Library/Python/3.6/lib/python/site-packages/sympy/functions/elementary/piecewise.py",
>  line 138, in __new__
>
>     r = cls.eval(*newargs)
>
>   File 
> "/Users/ndv/Library/Python/3.6/lib/python/site-packages/sympy/functions/elementary/piecewise.py",
>  line 187, in eval
>
>     c = c.as_set().as_relational(x)
>
>   File 
> "/Users/ndv/Library/Python/3.6/lib/python/site-packages/sympy/logic/boolalg.py",
>  line 146, in as_set
>
>     if periodicity(r, x) not in (0, None):
>
>   File 
> "/Users/ndv/Library/Python/3.6/lib/python/site-packages/sympy/calculus/util.py",
>  line 456, in periodicity
>
>     return periodicity(g, symbol)
>
>   File 
> "/Users/ndv/Library/Python/3.6/lib/python/site-packages/sympy/calculus/util.py",
>  line 473, in periodicity
>
>     g_s = decompogen(f, symbol)
>
>   File 
> "/Users/ndv/Library/Python/3.6/lib/python/site-packages/sympy/solvers/decompogen.py",
>  line 57, in decompogen
>
>     result += [f1] + decompogen(f2, symbol)
>
>   File 
> "/Users/ndv/Library/Python/3.6/lib/python/site-packages/sympy/solvers/decompogen.py",
>  line 57, in decompogen
>
>     result += [f1] + decompogen(f2, symbol)
>
>   File 
> "/Users/ndv/Library/Python/3.6/lib/python/site-packages/sympy/solvers/decompogen.py",
>  line 57, in decompogen
>
>     result += [f1] + decompogen(f2, symbol)
>
>   [Previous line repeated 960 more times]
>
>   File 
> "/Users/ndv/Library/Python/3.6/lib/python/site-packages/sympy/solvers/decompogen.py",
>  line 51, in decompogen
>
>     fp = Poly(f)
>
>   File 
> "/Users/ndv/Library/Python/3.6/lib/python/site-packages/sympy/polys/polytools.py",
>  line 129, in __new__
>
>     return cls._from_expr(rep, opt)
>
>   File 
> "/Users/ndv/Library/Python/3.6/lib/python/site-packages/sympy/polys/polytools.py",
>  line 239, in _from_expr
>
>     rep, opt = _dict_from_expr(rep, opt)
>
>   File 
> "/Users/ndv/Library/Python/3.6/lib/python/site-packages/sympy/polys/polyutils.py",
>  line 368, in _dict_from_expr
>
>     rep, gens = _dict_from_expr_no_gens(expr, opt)
>
>   File 
> "/Users/ndv/Library/Python/3.6/lib/python/site-packages/sympy/polys/polyutils.py",
>  line 311, in _dict_from_expr_no_gens
>
>     (poly,), gens = _parallel_dict_from_expr_no_gens((expr,), opt)
>
>   File 
> "/Users/ndv/Library/Python/3.6/lib/python/site-packages/sympy/polys/polyutils.py",
>  line 274, in _parallel_dict_from_expr_no_gens
>
>     gens = _sort_gens(gens, opt=opt)
>
>   File 
> "/Users/ndv/Library/Python/3.6/lib/python/site-packages/sympy/polys/polyutils.py",
>  line 106, in _sort_gens
>
>     gens = sorted(gens, key=order_key)
>
>   File 
> "/Users/ndv/Library/Python/3.6/lib/python/site-packages/sympy/polys/polyutils.py",
>  line 78, in order_key
>
>     gen = str(gen)
>
>   File 
> "/Users/ndv/Library/Python/3.6/lib/python/site-packages/sympy/core/basic.py", 
> line 412, in __str__
>
>     return sstr(self, order=None)
>
>   File 
> "/Users/ndv/Library/Python/3.6/lib/python/site-packages/sympy/printing/str.py",
>  line 847, in sstr
>
>     s = p.doprint(expr)
>
>   File 
> "/Users/ndv/Library/Python/3.6/lib/python/site-packages/sympy/printing/printer.py",
>  line 249, in doprint
>
>     return self._str(self._print(expr))
>
>   File 
> "/Users/ndv/Library/Python/3.6/lib/python/site-packages/sympy/printing/printer.py",
>  line 287, in _print
>
>     return getattr(self, printmethod)(expr, **kwargs)
>
>   File 
> "/Users/ndv/Library/Python/3.6/lib/python/site-packages/sympy/printing/str.py",
>  line 558, in _print_UnevaluatedExpr
>
>     return self._print(expr.args[0])
>
>   File 
> "/Users/ndv/Library/Python/3.6/lib/python/site-packages/sympy/printing/printer.py",
>  line 287, in _print
>
>     return getattr(self, printmethod)(expr, **kwargs)
>
> RecursionError: maximum recursion depth exceeded
>
> >>> sym.Piecewise((y,sym.UnevaluatedExpr(y)<1),(1,True))
>
> Traceback (most recent call last):
>
>   File "<stdin>", line 1, in <module>
>
>   File 
> "/Users/ndv/Library/Python/3.6/lib/python/site-packages/sympy/functions/elementary/piecewise.py",
>  line 138, in __new__
>
>     r = cls.eval(*newargs)
>
>   File 
> "/Users/ndv/Library/Python/3.6/lib/python/site-packages/sympy/functions/elementary/piecewise.py",
>  line 187, in eval
>
>     c = c.as_set().as_relational(x)
>
>   File 
> "/Users/ndv/Library/Python/3.6/lib/python/site-packages/sympy/logic/boolalg.py",
>  line 146, in as_set
>
>     if periodicity(r, x) not in (0, None):
>
>   File 
> "/Users/ndv/Library/Python/3.6/lib/python/site-packages/sympy/calculus/util.py",
>  line 456, in periodicity
>
>     return periodicity(g, symbol)
>
>   File 
> "/Users/ndv/Library/Python/3.6/lib/python/site-packages/sympy/calculus/util.py",
>  line 473, in periodicity
>
>     g_s = decompogen(f, symbol)
>
>   File 
> "/Users/ndv/Library/Python/3.6/lib/python/site-packages/sympy/solvers/decompogen.py",
>  line 57, in decompogen
>
>     result += [f1] + decompogen(f2, symbol)
>
>   File 
> "/Users/ndv/Library/Python/3.6/lib/python/site-packages/sympy/solvers/decompogen.py",
>  line 57, in decompogen
>
>     result += [f1] + decompogen(f2, symbol)
>
>   File 
> "/Users/ndv/Library/Python/3.6/lib/python/site-packages/sympy/solvers/decompogen.py",
>  line 57, in decompogen
>
>     result += [f1] + decompogen(f2, symbol)
>
>   [Previous line repeated 960 more times]
>
>   File 
> "/Users/ndv/Library/Python/3.6/lib/python/site-packages/sympy/solvers/decompogen.py",
>  line 51, in decompogen
>
>     fp = Poly(f)
>
>   File 
> "/Users/ndv/Library/Python/3.6/lib/python/site-packages/sympy/polys/polytools.py",
>  line 129, in __new__
>
>     return cls._from_expr(rep, opt)
>
>   File 
> "/Users/ndv/Library/Python/3.6/lib/python/site-packages/sympy/polys/polytools.py",
>  line 239, in _from_expr
>
>     rep, opt = _dict_from_expr(rep, opt)
>
>   File 
> "/Users/ndv/Library/Python/3.6/lib/python/site-packages/sympy/polys/polyutils.py",
>  line 368, in _dict_from_expr
>
>     rep, gens = _dict_from_expr_no_gens(expr, opt)
>
>   File 
> "/Users/ndv/Library/Python/3.6/lib/python/site-packages/sympy/polys/polyutils.py",
>  line 311, in _dict_from_expr_no_gens
>
>     (poly,), gens = _parallel_dict_from_expr_no_gens((expr,), opt)
>
>   File 
> "/Users/ndv/Library/Python/3.6/lib/python/site-packages/sympy/polys/polyutils.py",
>  line 274, in _parallel_dict_from_expr_no_gens
>
>     gens = _sort_gens(gens, opt=opt)
>
>   File 
> "/Users/ndv/Library/Python/3.6/lib/python/site-packages/sympy/polys/polyutils.py",
>  line 106, in _sort_gens
>
>     gens = sorted(gens, key=order_key)
>
>   File 
> "/Users/ndv/Library/Python/3.6/lib/python/site-packages/sympy/polys/polyutils.py",
>  line 78, in order_key
>
>     gen = str(gen)
>
>   File 
> "/Users/ndv/Library/Python/3.6/lib/python/site-packages/sympy/core/basic.py", 
> line 412, in __str__
>
>     return sstr(self, order=None)
>
>   File 
> "/Users/ndv/Library/Python/3.6/lib/python/site-packages/sympy/printing/str.py",
>  line 847, in sstr
>
>     s = p.doprint(expr)
>
>   File 
> "/Users/ndv/Library/Python/3.6/lib/python/site-packages/sympy/printing/printer.py",
>  line 249, in doprint
>
>     return self._str(self._print(expr))
>
>   File 
> "/Users/ndv/Library/Python/3.6/lib/python/site-packages/sympy/printing/printer.py",
>  line 287, in _print
>
>     return getattr(self, printmethod)(expr, **kwargs)
>
>   File 
> "/Users/ndv/Library/Python/3.6/lib/python/site-packages/sympy/printing/str.py",
>  line 558, in _print_UnevaluatedExpr
>
>     return self._print(expr.args[0])
>
>   File 
> "/Users/ndv/Library/Python/3.6/lib/python/site-packages/sympy/printing/printer.py",
>  line 287, in _print
>
>     return getattr(self, printmethod)(expr, **kwargs)
>
> RecursionError: maximum recursion depth exceeded
>
>
> Is there some way that I can do this, i.e. keep the unevaluated Piecewise 
> inside a cond of another piecewise?
>
>
> Best regards
>
> Nathaniel
>
>
> --
> You received this message because you are subscribed to the Google Groups 
> "sympy" group.
> To unsubscribe from this group and stop receiving emails from it, send an 
> email to [email protected].
> To post to this group, send email to [email protected].
> Visit this group at https://groups.google.com/group/sympy.
> To view this discussion on the web visit 
> https://groups.google.com/d/msgid/sympy/f149d06a-a6df-42c5-a848-c7bbe0c20a81%40googlegroups.com.
> For more options, visit https://groups.google.com/d/optout.

-- 
You received this message because you are subscribed to the Google Groups 
"sympy" group.
To unsubscribe from this group and stop receiving emails from it, send an email 
to [email protected].
To post to this group, send email to [email protected].
Visit this group at https://groups.google.com/group/sympy.
To view this discussion on the web visit 
https://groups.google.com/d/msgid/sympy/CAKgW%3D6JGXEJjjTzA_TC0B40MYPL8_DCJhWbjQBPWuFMZb4-Txw%40mail.gmail.com.
For more options, visit https://groups.google.com/d/optout.

Reply via email to