Intente ejecutar lo siguiente en JavaScript:

parseInt('01'); //equals 1
parseInt('02'); //equals 2
parseInt('03'); //equals 3
parseInt('04'); //equals 4
parseInt('05'); //equals 5
parseInt('06'); //equals 6
parseInt('07'); //equals 7
parseInt('08'); //equals 0 !!
parseInt('09'); //equals 0 !!

Acabo de enterarme por completo que JavaScript cree que el cero inicial indica un octal integer, y dado que hay no "8" o "9" en base-8, la función devuelve cero. Nos guste o no, esto es por diseño.

¿Cuáles son las soluciones alternativas?

Nota: En aras de la exhaustividad, estoy a punto de publicar una solución, pero es una solución que odio, así que publique otras / mejores respuestas.


Actualización:

La quinta edición del estándar de JavaScript (ECMA-262) presenta Un cambio radical que elimina este comportamiento. Mozilla tiene una buena escritura.

283
Portman 12 may. 2009 a las 02:14

10 respuestas

La mejor respuesta

Este es un problema común de Javascript con una solución simple:

Simplemente especifique la base, o 'radix' , al igual que:

parseInt('08',10); // 8

También puede usar Number:

Number('08'); // 8
326
groovecoder 3 mar. 2014 a las 18:26

¿Qué tal esto para decimal:

('09'-0) === 9  // true

('009'-0) === 9 // true
5
Mark Hall 20 ene. 2012 a las 03:28

Si sabe que su valor estará en el rango entero de 32 bits con signo, entonces ~~x hará lo correcto en todos los escenarios.

~~"08" === 8
~~"foobar" === 0
~~(1.99) === 1
~~(-1.99)  === -1

Si busca binario no (~), la especificación requiere una conversión "ToInt32" para el argumento que realiza la conversión obvia a Int32 y se especifica para obligar a los valores NaN a cero.

Sí, esto es increíblemente hack pero es muy conveniente ...

43
Karl Guertin 5 ene. 2010 a las 14:15
function parseDecimal(s) { return parseInt(s, 10); }

Editar: hacer su propia función, hacer lo que realmente quiere, es solo una opción si no le gusta agregar ", 10" todo el tiempo a la llamada parseInt (). Tiene la desventaja de ser una función no estándar: más conveniente para usted si la usa mucho, pero quizás más confusa para otros.

11
Jason S 11 may. 2009 a las 23:28

Si ya ha realizado una gran cantidad de codificación con parseInt y no desea agregar ", 10" a todo, puede anular la función para que la base 10 sea la predeterminada:

window._oldParseInt = window.parseInt;
window.parseInt = function(str, rad) {
    if (! rad) {
        return _oldParseInt(str, 10);
    }
    return _oldParseInt(str, rad);
};

Eso puede confundir a un lector posterior, por lo que hacer una función parseInt10 () podría explicarse más por sí mismo. Personalmente, prefiero usar una función simple que tener que agregar ", 10" todo el tiempo, solo crea más oportunidades para cometer errores.

4
ingredient_15939 17 jul. 2011 a las 06:05

Desde la documentación de parseInt, utilice el argumento de la raíz opcional para especificar base-10 :

parseInt('08', 10); //equals 8
parseInt('09', 10); //equals 9

Esto me parece pedante, confuso y detallado (¿realmente, un argumento adicional en cada análisis?), Así que espero que haya una mejor manera.

24
Portman 11 may. 2009 a las 22:16

También puede, en lugar de usar parseFloat o parseInt, usar el operador unario ( + ).

+"01"
// => 1

+"02"
// => 2

+"03"
// => 3

+"04"
// => 4

+"05"
// => 5

+"06"
// => 6

+"07"
// => 7

+"08"
// => 8

+"09"
// => 9

Y por si acaso

+"09.09"
// => 9.09

MDN Link

El operador unario más precede a su operando y lo evalúa, pero intenta convertirlo en un número, si aún no lo está. Aunque la negación unaria (-) también puede convertir no números, unario plus es la forma más rápida y preferida de convertir algo en un número , ya que no realiza ninguna otra operación en el número.

6
SoEzPz 17 may. 2019 a las 05:27

¿Sería muy malo reemplazar parseInt con una versión que asume decimal si no tiene un segundo parámetro? (nota - no probado)

parseIntImpl = parseInt
parseInt = function(str, base){return parseIntImpl(str, base ? base : 10)}
7
Andrew Duffy 12 may. 2009 a las 00:44

Especifique la base:

var number = parseInt(s, 10);
10
RichieHindle 11 may. 2009 a las 22:16

Este problema no se puede replicar en las últimas Chrome ni Firefox (2019).

0
Andrija 9 oct. 2019 a las 19:29