2

I don't have enough reputation points yet to leave comments, but saw numerous times when people (incorrectly) suggest using log10 to calculate the number of digits in a positive integer. This is wrong for large numbers!

long n = 99999999999999999L;

// correct answer: 17
int numberOfDigits = String.valueOf(n).length();

// incorrect answer: 18
int wrongNumberOfDigits = (int) (Math.log10(n) + 1); 
// also incorrect:
double wrongNumberOfDigits2 = Math.floor(Math.log10(n) + 1);

The logarithm-based solutions will incorrectly output 18 instead of 17.

I'd like to understand why.

Way to get number of digits in an int?
Fastest way to get number of digits on a number?

Community
  • 1
  • 1
moodcheerful
  • 195
  • 2
  • 7

2 Answers2

1

The problem is that 99999999999999999 cannot be exactly represented as a (double precision) floating-point value in this case. The nearest value is 1.0E+17 when passed as a double parameter to log10.

The same would be true of the log10(n) value: 16.999999999999999995657... - the nearest value that can be represented is 17.

Brett Hale
  • 21,653
  • 2
  • 61
  • 90
  • Thanks for the explanation! I wonder what the biggest long integer is where the logarithm-based solution will be correct? – moodcheerful Jan 15 '16 at 21:16
  • @moodcheerful - what you really want to ask is: what is the *range* of contiguous integer values that can be exactly represented? There's a good answer [here](http://stackoverflow.com/questions/1848700/biggest-integer-that-can-be-stored-in-a-double). – Brett Hale Jan 17 '16 at 14:52
1

It is mathematically absolutely correct.

Number of digit of any integer not null (positive !) is log10(n)+1. No doubt !

Problems arise with representations, as pointed by Brett Hale.

So, if you want, no problem, no limit, very accurate calculation :) use BigDecimal.

But simplest: use lengthof String:

Long l=99999999999999999L;
int len=l.toString().length();

If you really want to do calculation, see

that: Logarithm of a BigDecimal

that: BigDecimal to the power of BigDecimal on Java/Android

Community
  • 1
  • 1