-3

I am trying to multiply decimal value with 10 in Javascript:

console.log(1000.56 * 10);
console.log(100.56 * 10);

It is printing.

10005.59999999999
1005.6

Why?

Eric Postpischil
  • 195,579
  • 13
  • 168
  • 312
  • Check this out: https://en.wikipedia.org/wiki/Round-off_error, the way a floating point value is represented is its limit in this case – IvanF. May 11 '18 at 07:59
  • ```(1000.56 * 10).toFixed(1)``` – Shadow2531 May 11 '18 at 08:00
  • @baao , its not duplicate... – Manish Parab May 11 '18 at 08:05
  • Please elaborate why you think it's not exactly the same question – baao May 11 '18 at 08:06
  • @axiac , why same behavior is not repeated. – Manish Parab May 11 '18 at 08:06
  • @baao, for me lower value i.e 100.56 * 10 is producing different than higher value 1000.56 * 10 .. dont you think its different... Please read the description again...I have changed it... it would be helpful if you can remove the duplicate tag... – Manish Parab May 11 '18 at 08:10
  • No, it's explained in the answers pretty well – baao May 11 '18 at 08:14
  • In my example using pencil and paper, the error occurs because `1/3` does not have a finite representation in base `10`. `1000.56` has a finite representation in base `10` but its representation in base `2` is not finite; its value is approximated, the multiplication increases the error and for some numbers the error becomes larger enough to not be ignored. Your question is definitely one of the many hundreds of duplicates. – axiac May 11 '18 at 08:18
  • @axiac, i got the error concept in floating point, but what I'm not getting is when I initialize value to 1000.56 , its not 1000.5999999 ..C#, java understands it pretty well..but JS has different understanding – Manish Parab May 11 '18 at 08:24
  • Because of rounding errors, `100.056 * 10` is different than `1000.56`. C#, Java or PHP works the same as JavaScript. What differs is the amount of digits each language prints by default after the decimal dot. Less digits means a larger rounding that covers the difference between the stored value and the displayed value. Less digits means the program displays the value you want to see, not the real value (the difference is in the digits that are not displayed.) – axiac May 11 '18 at 08:29
  • @baao: Both of the numbers printed in this question differ from the ideal mathematical results due to floating-point rounding. Yet one of them prints a result matching the ideal result and one does not. The purported original and its answers do not contain information that really explains this. The answer is not just in the fact that floating-point operations round but in **how** they round and **how** various languages for at their outputs. Floating-pount questions need more specific answers than just “Floating-point has rounding errors, suffer with it.” – Eric Postpischil May 11 '18 at 11:47
  • @axiac: The mere fact that there are rounding errors does not explain why `console.log(100.56 * 10);` produces a result equal to the mathematically ideal result and `console.log(1000.56 * 10);` does not. The multiplication in the former produces a result that is not 1005.6, yet “1005.6” is printed. The purported original and its answerz do not explain this. – Eric Postpischil May 11 '18 at 11:51
  • @baao: [This](https://stackoverflow.com/questions/49711366/why-does-console-log-not-show-ieee-754-floating-point-value-of-assigned-var/49711490#49711490) is a closer original, although there is more needed to completely answer this question. Please do not promiscuously mark floating-point questions as duplictes of that other one. – Eric Postpischil May 11 '18 at 11:54
  • @axiac: [This](https://stackoverflow.com/questions/49711366/why-does-console-log-not-show-ieee-754-floating-point-value-of-assigned-var/49711490#49711490) is a closer original, although there is more needed to completely answer this question. Please do not promiscuously mark floating-point questions as duplictes of that other one. – Eric Postpischil May 11 '18 at 11:55
  • @EricPostpischil `console.log()` displays a limited number of digits for real numbers. It rounds the values to fit the number of digits and, for pretty results, trims the trailing `0`es. Use [`Number.toPrecision()`](https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/Number/toPrecision) with a value larger than `18` to find out that `1005.6` cannot be represented exactly but it is rounded to a value that is slightly bigger while `10005.6` is rounded to a value that is smaller and produces a larger rounding error. – axiac May 11 '18 at 12:03
  • `console.log(100.56 * 10); does not produce a result equal to the mathematically ideal result. It does some rounding that, for some values, happens to cover the error introduced by the floating point format while it doesn't cover the error for other values. – axiac May 11 '18 at 12:11
  • @axiac: (a) You are explaining the results in ways not covered in [that question](https://stackoverflow.com/questions/588004/is-floating-point-math-broken). Therefore, this one is not a duplicate. (b) In `console.log(100.56 * 10)`, `100.56 * 10` produces a result not equal to the mathematically ideal result, but this is not the final result. `console.log(100.56 * 10)` performs a convert-to-decimal operation, the reault of which is 1005.6, which is the mathematically ideal result. (You might not think of the formatting as a convert-to-decimal operation, but this is in fact what it is.) – Eric Postpischil May 11 '18 at 12:28
  • @EricPostpischil the floating point format uses approximations. It produces the mathematical exact value only for some inputs. An exact result is an exception, not the norm. Understanding this and understanding that the value displayed is an approximation of the approximation produced by the floating point format is the key here. – axiac May 11 '18 at 12:40
  • @axiac: Understanding that floating-point operations approximate real arithmetic (aside: as specified in IEEE 754: it is the **operations** that approximate real arithmetic, not the **format** that approximates real numbers) is a **part** of understanding the behavior. It is not the entire explanation, and that means this question, and most floating-point questions, are not duplicates of [that](https://stackoverflow.com/questions/588004/is-floating-point-math-broken) question. You would not answer all C questions as a duplicate of “Is C broken?” Do not do it for floating.point. – Eric Postpischil May 11 '18 at 12:44
  • @baao, in that case all the questions which has closure should be marked as duplicate as there is a wiki question for closure, same case with "use strict" .. use case here is different.. hence its not duplicate – Manish Parab May 11 '18 at 21:57
  • @ManishParab no, you dont have a glue on how this site works. Your question was and is bad and should not be prexerved! – baao May 11 '18 at 22:00
  • @baao can you tell me why my question is bad.. just because you think its bad.. and we forced you to remove duplicate tag . does not make it bad.. and please no personal comments... I respect community here.. and want to keep it that way – Manish Parab May 11 '18 at 22:06

1 Answers1

1

As explained in this question, JavaScript’s default behavior for converting floating-point numbers to decimal (when converting to a string, for display, printing, or other purposes), is to use just enough digits to uniquely identify the floating-point value.

In 1000.56 * 10, two rounding errors occur. The first occurs when 1000.56 is converted to floating point. The second occurs when the multiplication is performed. Two errors also occur in 100.56 * 10. However, the errors happen to partially cancel (they are in opposite directions, as an effectively random consequence of where representable values happen to lie), and the result is close enough to 1005.6 that JavaScript’s algorithm for formatting used “1005.6” for the result.

In 1000.56 * 10, the result was not the representable floating-point number closest to 10005.6, so JavaScript used additional digits to distinguish it.

Eric Postpischil
  • 195,579
  • 13
  • 168
  • 312