On Sun, 15 Jan 2023 at 16:12, Peter Stahlecker
<
peter.st...@gmail.com> wrote:
>
> Just to increase my understanding: why would one deprecate 'things' which work?
> Is this related to python's development?
Sometimes things sort of work in some cases but don't really work
properly and it isn't possible to fix them without breaking someone's
code.
Here is an example:
In [9]: t, s = symbols('t, s')
In [10]: L = LaplaceTransform(exp(t), t, s)
In [11]: print(L)
LaplaceTransform(exp(t), t, s)
In [12]: print(L.doit())
(1/(s - 1), 1, True)
Here L is an unevaluated LaplaceTransform object representing the
Laplace transform of exp(t). The LaplaceTransform.doit() method
attempts to return a tuple of 3 things representing not just the
transformed function but its region of convergence and any other
convergence conditions. That sort of makes sense until you realise
that the whole point of an unevaluated LaplaceTransform object is that
you can use it in expressions e.g.:
In [13]: print(2*L + 1)
2*LaplaceTransform(exp(t), t, s) + 1
In [14]: print((2*L + 1).doit())
~/current/sympy.git/sympy/core/operations.py:458: SymPyDeprecationWarning:
Using non-Expr arguments in Mul is deprecated (in this case, one of
the arguments has type 'Tuple').
If you really did intend to use a multiplication or addition operation with
this object, use the * or + operator instead.
See
https://docs.sympy.org/latest/explanation/active-deprecations.html#non-expr-args-deprecated
for details.
This has been deprecated since SymPy version 1.7. It
will be removed in a future version of SymPy.
...
[snip longer error message]
...
AttributeError: 'Tuple' object has no attribute 'as_coeff_Mul'
There are several problems here that demonstrate different points. The
fact that LaplaceTransform.doit turns an Expr until a Tuple means that
it will basically always do the wrong thing when used as part of an
expression. On the other hand anyone who might be using
LaplaceTransform.doit will have written their code to expect this
tuple so if we change it to return an expression instead of a tuple
then it will break their code.
So it is difficult to say precisely whether LaplaceTransform.doit is
"working". It is probably working for someone and they are using it to
do something useful. However it can't work in other situations and it
is clearly broken by design and needs to be changed. It isn't possible
to fix it without causing someone's code to break though.
Sometimes in this situation it would be possible to add a warning that
code will break in future so someone who is using
LaplaceTransform.doit() would see that warning. If we let that warning
get printed out for a few years then at that point we could change
SymPy's behaviour in a new release and hopefully people will have seen
the warning and already fixed their code. This is what it means to
"deprecate" something.
What this example also shows though is that in this case there is no
reasonable way for us to deprecate this and add a warning because we
can't make some alternative to the doit method which is a fundamental
part of SymPy. The only option is to make the change directly and that
will mean that some code that some other people have written might
stop working as a result. For some of those people it might seem as if
the current behaviour is "working" because the problems with the
current behaviour might not affect them.
Also what this example shows is one of the costs of leaving deprecated
functionality around which is that the call to doit should really
raise an immediate TypeError because a Tuple is not something that can
be multiplied. It does not though because the code that should raise
an error only gives a warning "Using non-Expr arguments in Mul is
deprecated". You can see why *that* is deprecated: the Mul code
expects Expr and expects its args to have methods like as_coeff_Mul so
allowing non-Expr here will lead to obscure failures. Following the
warning we have a confusing error message about a missing attribute
though when the correct one would be "Tuple cannot be in a Mul". We
don't currently give that error message because for now putting a
Tuple in a Mul is only "deprecated" rather than disallowed.
--
Oscar