Closed rizwanspeaks closed 6 years ago
If you do calculations with BigNumbers having 20 digits, you can up with a result having a precision less than 20 digits as rounding errors can occur.
For example, suppose you work with 2 digits precision and you calculate 1/3 + 1/3
,
you will get 0.33 + 0.33 = 0.66
whilst the correct answer would be 0.67
.
The solution is to always work with a higher precision than you need in the end. If you want 20 digits precision, work with 24 or 32 digits so you don't end up with round off errors in the first 20 digits.
In the below code
var resultAsNumber = math.number("2024244362894.73337782345");//2024244362894.7334`
math.number() method truncate the input by rounding the decimal by 4 digits. Is it possible to increase the rounding value.(I need 2024244362894.73337782345 as result instead of 2024244362894.7334
Note: Here I set the 'precision' value as 24
Regular numbers in JavaScript (and most programming languages) have a precision of about 16 digits. With math.number()
you convert the value to a regular number, which can't hold the 20 digits you want. You have to use BigNumbers for that. So, keep using resultAsDecimal
, don't create a resultAsNumber
.
If you want to get stringified output with a certain precision, you can use math.format
, like:
var precision = 20;
var resultAsString = math.format(inputValAsBigNum, precision);
See relevant docs: http://mathjs.org/docs/reference/functions/format.html http://mathjs.org/docs/datatypes/numbers.html http://mathjs.org/docs/datatypes/bignumbers.html
@josdejong what you think about double.js library for extended precision? Can it be usefull for math.js somehow?
@munrocket thanks for your suggestion. Do you see any advantages of double.js over decimal.js? (The latter is already available in mathjs)
Yep, it's much faster than decimal.js, but it handle only approximately 32 digits. It can be useful for heavy computation with double-double precision or as intermidiate format for numerical differentiation / matrix elimination.
That is definitely a valid reason. I'm not sure how common the need for double precision is though, in my experience 16 digits is just fine normally and the speed is important, and if numerical solutions get unstable due to round off errors they go unstable with some more digits too. But that's just my experience. I'm certainly open to add a new numeric type double.js
if there is a broad need for it.
An other numeric solution that sound really interesting to me is http://dec64.com/, which aims not just to have "more digits", but really addresses the round off issues that we typically have for example when working with money (you know the famous 0.1+0.2
I suppose...).
Very intresting link! Base 2 is too old and goes from Niklaus Virt. We need dec64 in hardware. Yep double.js can handle 0.1+0.2. But not all of them for now.
I am getting the result with losing precision when converting to the number). Note: [I am configured number as BigNumber and precision as 20]
` math.config({ number: 'bignumber', precision: 20 });
Here the expected result for resultAsNumber is 2024244362894.7333778 instead I am getting 2024244362894.7334 as result.