Search code examples
javascriptparseintproofparsefloat

parseInt() and parseFloat(): Can this second assertion ever fail?


I've been using parseInt() and parseFloat() in various contexts for a while now, and I'd like to think I know all the ins and outs of the two. But recently I had a curious thought which I so far haven't been able to definitively work out a proof for.

Consider the following function:

function testProof(strInteger) {
    assert(strInteger === '' + parseInt(strInteger, 10));

    assert(parseInt(strInteger, 10) === parseFloat(strInteger));
}

// Sample calls...
testProof("5");
testProof("109");
testProof("-55");

First we assert that converting the input to an integer and then converting back to a string produces the original string again. This guards against cases where parseInt("100bucks") returns 100, and it also makes sure there is no fractional part that's getting truncated off by the conversion -- we want to make sure that the input is actually a whole number, integer string.

If that succeeds, we then assert that parseInt(..., 10) returns the same value as parseFloat(...).

There are many reasons why the first assert would fail:

  • Input is not a whole number ("1.5")
  • Input has leading zeros ("0050")
  • Input has trailing garbage ("100bucks")
  • Input is in exponential notation ("1e3"), or it's so large it becomes exponential
  • Input is not parseable, resulting in NaN
  • Maybe others?

But here's the question: As long as the first assert passes, can the second assert ever fail? Put another way, if we know ahead of time that the input is an integer inside a string, can parseFloat(...) function as a drop-in replacement for parseInt(..., 10)? (Not saying it's a good replacement... :-P)


Solution

  • It actually can fail only with this input:

    testProof("NaN");
    

    But if you really know it's an integer, why the test? Also parseFloat can't be a good replacement for parseInt as in lots of cases you don't know if it's really an integer and not a float.