Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

want function for parsing an integer #7

Closed
davepacheco opened this issue Sep 3, 2015 · 1 comment
Closed

want function for parsing an integer #7

davepacheco opened this issue Sep 3, 2015 · 1 comment

Comments

@davepacheco
Copy link
Contributor

There are a few common ways of parsing an integer in JavaScript, but they have their caveats, and error handling is tricky. It would be good to have a single function for doing this robustly.

Cases to consider:

> parseInt('13f') /* does not fail with invalid input */
13

> Number('') /* does not fail with empty input */
0
@davepacheco
Copy link
Contributor Author

davepacheco commented Feb 23, 2017

I think @melloc is working on this.

There have obviously been a bunch of half-baked implementations of this. I think it's important that we identify and deal with the various edge cases so that we don't repeat the same mistakes. I also think this function should be able to support the various options people need (e.g., hex, octal, looseness with leading and trailing whitespace, and so on). It doesn't have to do all of these at first, but it should be extendable to do that later. Otherwise, people who need this will just stop using this function and re-introduce all the old issues with parseInt() and Number().

I wrote up some sample documentation:

### parseInt(str, options)

Parses the contents of "str" (a string) as an integer.  On success, the integer value is returned (as a number).  On failure, an error is **returned** describing the problem.

By default, leading and trailing whitespace are not allowed, nor are trailing invalid characters.  The empty string (`''`) is not considered valid input.  If the return value cannot be precisely represented as a number (i.e., is smaller than `Number.MIN_SAFE_INTEGER` or larger than `Number.MAX_SAFE_INTEGER`), an error is returned.  (Future versions could provide options for this behavior.)

The following may be specified in "options":

Option   | Type   | Default | Meaning
------   | ------ | ------- | ------
base     | number | 10      | numeric base to use.  If this has the value 'auto', then the base will be inferred from the string itself the way `parseInt` works without a radix parameter.  This behavior can be surprising when the input source (e.g., a human) doesn't realize that a leading `0` implies an octal value.

**Context:** It's tricky to parse integers with JavaScript's built-in facilities
for several reasons:

- `parseInt()` by default allows the base to be specified in the input string by
  a prefix (e.g., `0x` for hex).  This is convenient for programmer-specified
  values that might be bitfields or file permissions, but end users can easily
  include a `0` prefix while still intending base-10, resulting in the wrong
  behavior.
- `parseInt()` allows trailing non-numeric characters.  This can be useful in
  some cases, but isn't a great default.
- `Number(str)` returns 0 when `str` is the empty string (`''`).
- Both `parseInt()` and `Number()` return incorrect values when the input string
  represents a valid integer outside the range of integers that can be
  represented precisely.  Specifically, `parseInt('9007199254740993')` is
  9007199254740992.

I only discovered the MAX_SAFE_INTEGER issue when I started writing test cases for boundary conditions. We may find more of these as we continue to do that.

joyent-automation pushed a commit that referenced this issue Mar 13, 2017
Reviewed by: Dave Pacheco <dap@joyent.com>
Approved by: Dave Pacheco <dap@joyent.com>
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

No branches or pull requests

1 participant