jiggzson / nerdamer

a symbolic math expression evaluator for javascript
http://www.nerdamer.com
MIT License
517 stars 82 forks source link

The expression equals API fails with following expressions #543

Closed bbmarkus closed 3 years ago

bbmarkus commented 4 years ago

Version: 1.1.4

JS fiddle: https://jsfiddle.net/db1th5yc/ (copied from documentation page for nerdamer(x).eq(y), added two expressions at the end).

var x = nerdamer('4*(x+1)*(x+4)').eq('4*x^2+20*x+16');
console.log(x.toString());
var x = nerdamer('(x+1)*(x-1)').eq('x^2-1'); // (a+b)(a-b) = a^2-b^2
console.log(x.toString());

Expected result: for these two to return true, the second one is a fairly well known factorisation/simplification formula 🙂. Note, solving 4*(x+1)*(x+4) = y for y does return 4*x^2+20*x+16 (or rather 16+20*x+4*x^2, which is the same thing).

While I was looking into this, I also found that nerdamer.tree(expr) for the variant: "4(x+1)(x+4)" returns strange results (i.e. doesn't work with implied multiplication), but that seems like a separate issue.

jiggzson commented 4 years ago

Thanks. I think a more appropriate approach to eq would be to expand both sides and then test for equality. I'm not sure if that's how it's currently done. I see what you mean about 4(x+1)(x+4). It's worth looking into a bit.

bbmarkus commented 4 years ago

@jiggzson you are correct using expand() as part of the input does resolve the issue with eq, but shouldn't that be something that eq would always do? (make it an optional argument and it won't break any existing use cases 🙂, if that is important).

Here is an opinionated follow up question: should there be a code equivalent apis for at least expand and simplify? (in our use case it feels a bit weird "editing" the input, especially if it is already an expression, that is coming from elsewhere to wrap it with a function that as far as I can see is only available as a math function.

jiggzson commented 4 years ago

but shouldn't that be something that eq would always do?

Correct. That's what I was saying. To make it the default behavior. I can't see why it would break existing use cases.

Here is an opinionated follow up question: should there be a code equivalent apis for at least expand and simplify?

Not sure what you mean. You can already so something like the following.

var ans = nerdamer.expand('4*(x+1)*(x+4)');
console.log(ans.toString());
var ans2 = nerdamer.simplify('16+20*x+4*x^2');
console.log(ans2.toString());

Or are you proposing something else?

bbmarkus commented 4 years ago

Not sure what you mean. You can already so something like the following.

Oh you can, the documentation doesn't mention that, but now that I look at it closely it might be bit behind (IIRC it doesn't list nerdamer.rpn() for instance, which looking at the code seems to be a thing).

I was basically looking for something like: nerdamer.convertFromLaTeX(input).simplify(); Now looking at Expression in code, expand() seems to be there but simplify looks presently absent.

jiggzson commented 4 years ago

It does somewhat vaguely mentions that at the top of the documentation page with this var x = nerdamer.diff('sin(x)/x', 'x'); line. It's also peppered throughout the documentation pages as examples but you're right, it should be documented a little better.

I was basically looking for something like: nerdamer.convertFromLaTeX(input).simplify();

I see. Got it.