Skip to content

Commit 20678c4

Browse files
authored
Merge pull request #762 from MaxFreedomPollard/fix-numdigits-zero-and-one
Fix Util.numDigits returning 0 for 0 and 1, and 18 for 1E18
2 parents 90319c2 + accfafb commit 20678c4

2 files changed

Lines changed: 35 additions & 7 deletions

File tree

‎src/main/java/org/apache/datasketches/common/Util.java‎

Lines changed: 15 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -798,13 +798,21 @@ public static int bitAt(final long number, final int bitPos) {
798798
/** Decimal Digits ***************************/
799799

800800
/**
801-
* Computes the number of decimal digits of the number n
802-
* @param n the given number
803-
* @return the number of decimal digits of the number n
804-
*/
805-
public static int numDigits(long n) {
806-
if ((n % 10) == 0) { n++; }
807-
return (int) ceil(log(n) / log(10));
801+
* Computes the minimum number of characters required to print the number n as a decimal.
802+
* Negative numbers add one for the minus sign character.
803+
* No other non-digit characters are assumed.
804+
* @param n the given number, which may be negative.
805+
* @return the number of characters required to print the number n as a decimal
806+
*/
807+
public static int numDigits(final long n) {
808+
if (n == 0) { return 1; } //handles the zero special case
809+
int count = (n < 0) ? 1 : 0; //handles the minus sign
810+
long v = n;
811+
while (v != 0) {
812+
v /= 10;
813+
count++;
814+
}
815+
return count;
808816
}
809817

810818
/** Generic relational tests *****************/

‎src/test/java/org/apache/datasketches/common/UtilTest.java‎

Lines changed: 20 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -46,6 +46,7 @@
4646
import static org.apache.datasketches.common.Util.longToBytes;
4747
import static org.apache.datasketches.common.Util.milliSecToString;
4848
import static org.apache.datasketches.common.Util.nanoSecToString;
49+
import static org.apache.datasketches.common.Util.numDigits;
4950
import static org.apache.datasketches.common.Util.numberOfLeadingOnes;
5051
import static org.apache.datasketches.common.Util.numberOfTrailingOnes;
5152
import static org.apache.datasketches.common.Util.powerSeriesNextDouble;
@@ -241,6 +242,25 @@ public void checkCharacterPad() {
241242
assertEquals(out,"zzzzzzzzzzzzPad 30, prepend z:");
242243
}
243244

245+
/**
246+
* Check all the transition points where the number of decimal characters change.
247+
*/
248+
@Test
249+
public void checkNumDigits() {
250+
for (long n = 1; n > 0; n *= 10) { //n goes negative on rollover, which halts the loop
251+
checkN(n);
252+
checkN(n - 1);
253+
checkN(-n);
254+
checkN(-n + 1);
255+
}
256+
checkN(Long.MAX_VALUE);
257+
checkN(Long.MIN_VALUE);
258+
}
259+
260+
private static void checkN(final long n) {
261+
assertEquals(numDigits(n), String.valueOf(n).length());
262+
}
263+
244264
@Test
245265
public void checkProbabilityFn1() {
246266
checkProbability(.5, "Good");

0 commit comments

Comments
 (0)