It would really be a shame to give up the name solve(). Maybe we can put this on a list of big changes that we can do in 2.0? Although it would be good to have a working replacement ready before we do any renaming.
On Fri, Mar 4, 2022 at 8:27 AM Oscar Benjamin <[email protected]> wrote: > > On Fri, 4 Mar 2022 at 14:57, Chris Smith <[email protected]> wrote: > > > > We could just make a wrapper named `solved = lambda f,*s,**k: solve(f, *s, > > **k, dict=True)` > > If there is to be a new API then there are a *lot* of other things > that I would want to change about it compared to solve so it > definitely wouldn't be just a thin wrapper around solve. It would be > nice if nonlinsolve could be the new API but it doesn't have good > return types either. It might be helpful to enumerate some of those things. Here are a few I've noticed - In general, the output of solve() should not depend on the specific mathematical type of the input. This means for instance, linear and nonlinear equations should be handled in the exact same way. Right now, even dict=True can't save you: >>> solve([x**2 - 2, x > 1], x) Eq(x, sqrt(2)) >>> solve([x**2 - 2, x > 1], x, dict=True) Eq(x, sqrt(2)) One can imagine wanting to use x > 1 just to limit the solutions (which can't be done just with the old assumptions), but this has caused solve() to treat it as a completely different type of equation. - One issue I see is that it's not always clear what solve() will/should do in some cases, especially undetermined cases. It seems like "solving" and "variable elimination" are too often mixed together. It would be better if they were completely separated, since it's not clear to me why you would want one when solve can't produce the other. We should very carefully define what it means to "solve" an equation (note this is not so trivial once you include systems, multiple variables, infinite solutions, and inequalities into the mix). - Similarly, solve() should "refuse the temptation to guess". In an API like diff() or integrate(), you are allowed to pass a single expression without a variable, but only in the case where the expression has a single variable. In all other cases, it raises an exception and forces the user to provide a variable. But consider solve >>> solve(x*y - y) [{x: 1}, {y: 0}] Here solve(x*y - y) could mean one of three things: "solve for x", "solve for y", or "solve for x and y simultaneously". solve() has decided to do the latter. But what's worse, consider a similar example: >>> solve(sin(x)*x - y) [{y: x*sin(x)}] Now solving for x and y simultaneously is impossible, as is solving for x, so solve() has just picked the one that it knows how to do and solved for y. Both of the above should be an error. The user should be required to specify which variable(s) they want to solve for in ambiguous cases like this. - It would be nice to have an API that can work uniformly even in cases where there are infinitely many solutions (both parametric and inequality). The traditional solution to this has been solveset(), which definitely fixes the "uniform API" problem, but the issue is that the outputs of it aren't exactly easy to manipulate programmatically. There's also no guarantees at all about the exact format of a solveset() output. It might be a ConditionSet or an ImageSet or some Union. One idea is to make things programmatic with some sort of Solution object that provides different things like solution parameters in consistent attributes. This would also allow moving some of the more complex keyword-arguments from solve() itself into methods of the Solution object. - The API should also work uniformly for systems as well as single equations. Perhaps the cleanest way would be for solve() to always treat a single equation as a system of one equation. That way the return type is always uniform (the downside is the common case might involve an extra layer of indirection, which could be annoying). There's also this old issue "solve is a mess" which discusses a lot of these things. https://github.com/sympy/sympy/issues/6659 Aaron Meurer > > -- > Oscar > > -- > 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 view this discussion on the web visit > https://groups.google.com/d/msgid/sympy/CAHVvXxRY4xwA-ST6BDjFLfiOwWykj2eLW_iFhzsfEbmAK%3DSTVQ%40mail.gmail.com. -- 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 view this discussion on the web visit https://groups.google.com/d/msgid/sympy/CAKgW%3D6LGXj_c_dnsujrApcN05rZ79bUr8BCWM4c1am4SDG-WQw%40mail.gmail.com.
