numbers.md (3879B)
1 # Numbers 2 3 Math.js supports three types of numbers: 4 5 - Number for fast floating point arithmetic, described on this page. 6 - BigNumber for arbitrary precision arithmetic, described on the page 7 [BigNumbers](bignumbers.md). 8 - Fraction, which stores numbers in terms of a numerator and denominators, 9 described on the page [Fractions](fractions.md). 10 11 12 ## Configuration 13 14 Most functions can determine the type of output from the type of input: 15 a number as input will return a number as output, a BigNumber as input returns 16 a BigNumber as output. Functions which cannot determine the type of output 17 from the input (for example `math.evaluate`) use the default number type, which 18 can be configured when instantiating math.js: 19 20 ```js 21 math.config({ 22 number: 'number' // Default type of number: 23 // 'number' (default), 'BigNumber', or 'Fraction' 24 }) 25 ``` 26 27 ## Round-off errors 28 29 Math.js uses the built-in JavaScript Number type. A Number is a floating point 30 number with a limited precision of 64 bits, about 16 digits. The largest integer 31 number which can be represented by a JavaScript Number 32 is `+/- 9007199254740992` (`+/- 2^53`). Because of the limited precision of 33 floating point numbers round-off errors can occur during calculations. 34 This can be easily demonstrated: 35 36 ```js 37 // a round-off error 38 0.1 + 0.2 // 0.30000000000000004 39 math.add(0.1, 0.2) // 0.30000000000000004 40 ``` 41 42 In most cases, round-off errors don't matter: they have no significant 43 impact on the results. However, it looks ugly when displaying output to a user. 44 A solution is to limit the precision just below the actual precision of 16 45 digits in the displayed output: 46 47 ```js 48 // prevent round-off errors showing up in output 49 const ans = math.add(0.1, 0.2) // 0.30000000000000004 50 math.format(ans, {precision: 14}) // '0.3' 51 ``` 52 53 Alternatives are to use [Fractions](fractions.md) which store a number as a numerator and denominator, or [BigNumbers](bignumbers.md), which store a number with a higher precision. 54 55 56 ## Minimum and maximum 57 58 A Number can store values between `5e-324` and `1.7976931348623157e+308`. 59 Values smaller than the minimum are stored as `0`, and values larger than the 60 maximum are stored as `+/- Infinity`. 61 62 ```js 63 // exceeding the maximum and minimum number 64 console.log(1e309) // Infinity 65 console.log(1e-324) // 0 66 ``` 67 68 ## Equality 69 70 Because of rounding errors in calculations, it is unsafe to compare JavaScript 71 Numbers. For example executing `0.1 + 0.2 == 0.3` in JavaScript will return 72 false, as the addition `0.1 + 0.2` introduces a round-off error and does not 73 return exactly `0.3`. 74 75 To solve this problem, the relational functions of math.js check whether the 76 relative difference between the compared values is smaller than the configured 77 option `epsilon`. In pseudo code (without exceptions for 0, Infinity and NaN): 78 79 diff = abs(x - y) 80 nearlyEqual = (diff <= max(abs(x), abs(y)) * EPSILON) OR (diff < DBL_EPSILON) 81 82 where: 83 84 - `EPSILON` is the relative difference between x and y. Epsilon is configurable 85 and is `1e-12` by default. See [Configuration](../core/configuration.md). 86 - `DBL_EPSILON` is the minimum positive floating point number such that 87 `1.0 + DBL_EPSILON !== 1.0`. This is a constant with a value of approximately 88 `2.2204460492503130808472633361816e-16`. 89 90 Note that the relational functions cannot be used to compare small values 91 (`< 2.22e-16`). These values are all considered equal to zero. 92 93 Examples: 94 95 ```js 96 // compare values having a round-off error 97 console.log(0.1 + 0.2 === 0.3) // false 98 console.log(math.equal(0.1 + 0.2, 0.3)) // true 99 100 // small values (< 2.22e-16) cannot be compared 101 console.log(3e-20 === 3.1e-20) // false 102 console.log(math.equal(3e-20, 3.1e-20)) // true 103 ``` 104 105 The available relational functions are: `compare`, `equal`, `larger`, 106 `largerEq`, `smaller`, `smallerEq`, `unequal`.