(Incorporado) en JavaScript para verificar si una cadena es un número válido

Espero que haya algo en el mismo espacio conceptual que la antigua función VB6 IsNumeric() .

Para verificar si una variable (incluyendo una cadena) es un número, verifique si no es un número:

Esto funciona independientemente de si la variable contiene una cadena o número.

 isNaN(num) // returns true if the variable does NOT contain a valid number 

Ejemplos

 isNaN(123) // false isNaN('123') // false isNaN('1e10000') // false (This translates to Infinity, which is a number) isNaN('foo') // true isNaN('10px') // true 

Por supuesto, puede negar esto si lo necesita. Por ejemplo, para implementar el ejemplo IsNumeric que dio:

 function isNumeric(num){ return !isNaN(num) } 

Para convertir una cadena que contiene un número en un número:

solo funciona si la cadena solo contiene caracteres numéricos, de lo contrario, devuelve NaN .

 +num // returns the numeric value of the string, or NaN // if the string isn't purely numeric characters 

Ejemplos

 +'12' // 12 +'12.' // 12 +'12..' // Nan +'.12' // 0.12 +'..12' // Nan +'foo' // NaN +'12px' // NaN 

Para convertir una cadena libremente en un número

útil para convertir ’12px’ a 12, por ejemplo:

 parseInt(num) // extracts a numeric value from the // start of the string, or NaN. 

Ejemplos

 parseInt('12') // 12 parseInt('aaa') // NaN parseInt('12px') // 12 parseInt('foo2') // NaN These last two may be different parseInt('12a5') // 12 from what you expected to see. 

Flotadores

Tenga en cuenta que, a diferencia de +num , parseInt (como su nombre indica) convertirá un flotante en un entero al cortar todo lo que sigue al punto decimal (si desea usar parseInt() debido a este comportamiento, probablemente sea mejor usando otro método en su lugar ):

 +'12.345' // 12.345 parseInt(12.345) // 12 parseInt('12.345') // 12 

Cadenas vacías

Las cadenas vacías pueden ser un poco contra-intuitivas. +num convierte cadenas vacías a cero, e isNaN() asume lo mismo:

 +'' // 0 isNaN('') // false 

Pero parseInt() no está de acuerdo:

 parseInt('') // NaN 

Y podrías ir al RegExp-way:

 var num = "987238"; if(num.match(/^-{0,1}\d+$/)){ //valid integer (positive or negative) }else if(num.match(/^\d+\.\d+$/)){ //valid float }else{ //not valid number } 

Si realmente desea asegurarse de que una cadena contiene solo un número, cualquier número (entero o punto flotante) y exactamente un número, no puede usar parseInt() / parseFloat() , Number() o !isNaN() por sí mismos. Tenga en cuenta que !isNaN() realmente devuelve true cuando Number() devolvería un número y false cuando devolvería NaN , por lo que lo excluiré del rest de la discusión.

El problema con parseFloat() es que devolverá un número si la cadena contiene cualquier número, incluso si la cadena no contiene solo y exactamente un número:

 parseFloat("2016-12-31") // returns 2016 parseFloat("1-1") // return 1 parseFloat("1.2.3") // returns 1.2 

El problema con Number() es que devolverá un número en los casos en que el valor pasado no sea un número en absoluto.

 Number("") // returns 0 Number(" ") // returns 0 Number(" \u00A0 \t\n\r") // returns 0 

El problema con el despliegue de su propia expresión regular es que, a menos que cree la expresión regular exacta para hacer coincidir un número de punto flotante, como Javascript lo reconoce, se perderán casos o se reconocerán casos en los que no debería hacerlo. E incluso si puedes sacar tu propia expresión regular, ¿por qué? Hay formas integradas más simples de hacerlo.

Sin embargo, resulta que Number() (e isNaN() ) hacen lo correcto para cada caso donde parseFloat() devuelve un número cuando no debería, y viceversa. Entonces, para saber si una cadena es realmente exactamente y solo un número, llame a ambas funciones y vea si ambas devuelven la verdad:

 function isNumber(str) { if (typeof str != "string") return false // we only process strings! // could also coerce to string: str = ""+str return !isNaN(str) && !isNaN(parseFloat(str)) } 

Pruebe la función isNan :

La función isNaN () determina si un valor es un número ilegal (No es un número).

Esta función devuelve verdadero si el valor equivale a NaN. De lo contrario, devuelve falso.

Esta función es diferente del método Número específico Number.isNaN () .

La función global esNaN (), convierte el valor probado a un Número y luego lo prueba.

Number.isNan () no convierte los valores a un Número, y no devolverá verdadero para ningún valor que no sea del tipo Número …

Si solo está tratando de verificar si una cadena es un número entero (sin decimales), la expresión regular es una buena forma de hacerlo. Otros métodos como isNaN son demasiado complicados para algo tan simple.

 function isNumeric(value) { return /^-{0,1}\d+$/.test(value); } console.log(isNumeric('abcd')); // false console.log(isNumeric('123a')); // false console.log(isNumeric('1')); // true console.log(isNumeric('1234567890')); // true console.log(isNumeric('-23')); // true console.log(isNumeric(1234)); // true console.log(isNumeric('123.4')); // false console.log(isNumeric('')); // false console.log(isNumeric(undefined)); // false console.log(isNumeric(null)); // false 

Para permitir solo números enteros positivos use esto:

 function isNumeric(value) { return /^\d+$/.test(value); } console.log(isNumeric('123')); // true console.log(isNumeric('-23')); // false 

Una vieja pregunta, pero faltan varios puntos en las respuestas dadas.

Notación cientifica.

!isNaN('1e+30') es true , sin embargo, en la mayoría de los casos, cuando las personas piden números, no quieren hacer coincidir cosas como 1e+30 .

Los grandes números flotantes pueden comportarse de manera extraña

Observe (usando Node.js):

 > var s = Array(16 + 1).join('9') undefined > s.length 16 > s '9999999999999999' > !isNaN(s) true > Number(s) 10000000000000000 > String(Number(s)) === s false > 

Por otra parte:

 > var s = Array(16 + 1).join('1') undefined > String(Number(s)) === s true > var s = Array(15 + 1).join('9') undefined > String(Number(s)) === s true > 

Entonces, si uno espera String(Number(s)) === s , entonces mejor limite sus cadenas a 15 dígitos como máximo (después de omitir los ceros a la izquierda).

infinito

 > typeof Infinity 'number' > !isNaN('Infinity') true > isFinite('Infinity') false > 

Dado todo eso, verificando que la cadena dada sea un número que satisfaga todo lo siguiente:

  • notación no científica
  • conversión predecible a Number y volver a String
  • finito

no es una tarea tan fácil. Aquí hay una versión simple:

  function isNonScientificNumberString(o) { if (!o || typeof o !== 'string') { // Should not be given anything but strings. return false; } return o.length < = 15 && o.indexOf('e+') < 0 && o.indexOf('E+') < 0 && !isNaN(o) && isFinite(o); } 

Sin embargo, incluso este está lejos de ser completo. Los ceros a la izquierda no se manejan aquí, pero se atornillan la prueba de longitud.

parseInt (), pero tenga en cuenta que esta función es un poco diferente en el sentido de que, por ejemplo, devuelve 100 para parseInt (“100px”).

Puede usar el resultado de Number cuando pasa un argumento a su constructor.

Si el argumento (una cadena) no se puede convertir en un número, devuelve NaN, por lo que puede determinar si la cadena proporcionada fue un número válido o no.

Notas: Tenga en cuenta al pasar cadena vacía o '\t\t' y '\n\t' ya que Number devolverá 0; Pasar true arrojará 1 y devuelve falso 0.

  Number('34.00') // 34 Number('-34') // -34 Number('123e5') // 12300000 Number('123e-5') // 0.00123 Number('999999999999') // 999999999999 Number('9999999999999999') // 10000000000000000 (integer accuracy up to 15 digit) Number('0xFF') // 255 Number('Infinity') // Infinity Number('34px') // NaN Number('xyz') // NaN Number('true') // NaN Number('false') // NaN // cavets Number(' ') // 0 Number('\t\t') // 0 Number('\n\t') // 0 

Tal vez haya una o dos personas que se crucen con esta pregunta y necesiten un control mucho más estricto de lo normal (como yo). En ese caso, esto podría ser útil:

 if(str === String(Number(str))) { // it's a "perfectly formatted" number } 

¡Tener cuidado! Esto rechazará cadenas como .1 , 40.000 , 080 , 00.1 . Es muy exigente: la cuerda debe coincidir con la ” forma mínima más perfecta ” para que pase esta prueba.

Utiliza el constructor de String y Number para convertir la cadena en un número y viceversa, y así verifica si la “forma mínima perfecta” del motor de JavaScript (la que se convirtió con el constructor inicial del Number ) coincide con la cadena original.

He probado y la solución de Michael es la mejor. Vota por su respuesta anterior (busca en esta página “Si realmente quieres asegurarte de que haya una cuerda” para encontrarla). En esencia, su respuesta es esta:

 function isNumeric(num){ num = "" + num; //coerce num to be a string return !isNaN(num) && !isNaN(parseFloat(num)); } 

Funciona para todos los casos de prueba, que documenté aquí: https://jsfiddle.net/wggehvp9/5/

Muchas de las otras soluciones fallan para estos casos extremos: ”, nulo, ”, verdadero y []. En teoría, podría usarlos, con el manejo adecuado de errores, por ejemplo:

 return !isNaN(num); 

o

 return (+num === +num); 

con manejo especial para / \ s /, null, “”, true, false, [] (y otros?)

Bueno, estoy usando este que hice …

Ha estado funcionando hasta ahora:

 function checkNumber(value) { if ( value % 1 == 0 ) return true; else return false; } 

Si detecta algún problema con él, dígame, por favor.

Citar:

isNaN (num) // devuelve verdadero si la variable NO contiene un número válido

no es del todo cierto si necesita verificar espacios iniciales / finales, por ejemplo, cuando se requiere cierta cantidad de dígitos, y necesita obtener, por ejemplo, ‘1111’ y no ‘111’ o ‘111’ para tal vez un PIN entrada.

Mejor usar:

 var num = /^\d+$/.test(num) 

¿Por qué la implementación de jQuery no es lo suficientemente buena?

 function isNumeric(a) { var b = a && a.toString(); return !$.isArray(a) && b - parseFloat(b) + 1 >= 0; }; 

Michael sugirió algo como esto (aunque he robado la versión modificada de “user1691651 – John” aquí):

 function isNumeric(num){ num = "" + num; //coerce num to be a string return !isNaN(num) && !isNaN(parseFloat(num)); } 

La siguiente es una solución con el más probable mal desempeño, pero resultados sólidos. Es un artilugio hecho a partir de la implementación de jQuery 1.12.4 y la respuesta de Michael, con una verificación adicional para los espacios iniciales / finales (porque la versión de Michael devuelve verdadera para los valores numéricos con espacios iniciales / finales):

 function isNumeric(a) { var str = a + ""; var b = a && a.toString(); return !$.isArray(a) && b - parseFloat(b) + 1 >= 0 && !/^\s+|\s+$/g.test(str) && !isNaN(str) && !isNaN(parseFloat(str)); }; 

La última versión tiene dos nuevas variables, sin embargo. Uno podría esquivar a uno de ellos haciendo lo siguiente:

 function isNumeric(a) { if ($.isArray(a)) return false; var b = a && a.toString(); a = a + ""; return b - parseFloat(b) + 1 >= 0 && !/^\s+|\s+$/g.test(a) && !isNaN(a) && !isNaN(parseFloat(a)); }; 

No he probado mucho de esto, por otros medios que no sea la prueba manual de los pocos casos de uso que voy a tener con mi situación actual, que es todo lo estándar. Esta es una situación “de pie sobre los hombros de gigantes”.

PFB la solución de trabajo:

  function(check){ check = check + ""; var isNumber = check.trim().length>0? !isNaN(check):false; return isNumber; } 

Mi bash de una solución ligeramente confusa, tal vez no la mejor

 function isInt(a){ return a === ""+~~a } console.log(isInt('abcd')); // false console.log(isInt('123a')); // false console.log(isInt('1')); // true console.log(isInt('0')); // true console.log(isInt('-0')); // false console.log(isInt('01')); // false console.log(isInt('10')); // true console.log(isInt('-1234567890')); // true console.log(isInt(1234)); // true console.log(isInt('123.4')); // false console.log(isInt('')); // false // other types then string returns false console.log(isInt(5)); // false console.log(isInt(undefined)); // false console.log(isInt(null)); // false console.log(isInt('0x1')); // false console.log(isInt(Infinity)); // false 

Si alguien llega a llegar tan lejos, pasé algún tiempo pirateando este bash de parchar el momento.js ( https://github.com/moment/moment ). Aquí hay algo que le quité:

 function isNumeric(val) { var _val = +val; return (val !== val + 1) //infinity check && (_val === +val) //Cute coercion check && (typeof val !== 'object') //Array/object check } 

Maneja los siguientes casos:

¡Cierto! :

 isNumeric("1")) isNumeric(1e10)) isNumeric(1E10)) isNumeric(+"6e4")) isNumeric("1.2222")) isNumeric("-1.2222")) isNumeric("-1.222200000000000000")) isNumeric("1.222200000000000000")) isNumeric(1)) isNumeric(0)) isNumeric(-0)) isNumeric(1010010293029)) isNumeric(1.100393830000)) isNumeric(Math.LN2)) isNumeric(Math.PI)) isNumeric(5e10)) 

¡Falso! :

 isNumeric(NaN)) isNumeric(Infinity)) isNumeric(-Infinity)) isNumeric()) isNumeric(undefined)) isNumeric('[1,2,3]')) isNumeric({a:1,b:2})) isNumeric(null)) isNumeric([1])) isNumeric(new Date())) 

Irónicamente, el que más me cuesta:

 isNumeric(new Number(1)) => false 

Cualquier sugerencia bienvenida :]

Me gusta la simplicidad de esto.

 Number.isNaN(Number(value)) 

Lo anterior es un Javascript regular, pero estoy usando esto junto con un typeguard tipográfico para la verificación inteligente de tipos. Esto es muy útil para que el comstackdor typescript le proporcione el intellisense correcto, y no escriba ningún tipo de error.

Guardagujas tipográficos

 isNotNumber(value: string | number): value is string { return Number.isNaN(Number(this.smartImageWidth)); } isNumber(value: string | number): value is number { return Number.isNaN(Number(this.smartImageWidth)) === false; } 

Supongamos que tiene un width propiedad que es number | string number | string . Es posible que desee hacer lógica en función de si es una cadena o no.

 var width: number|string; width = "100vw"; if (isNotNumber(width)) { // the compiler knows that width here must be a string if (width.endsWith('vw')) { // we have a 'width' such as 100vw } } else { // the compiler is smart and knows width here must be number var doubleWidth = width * 2; } 

El typeguard es lo suficientemente inteligente como para limitar el tipo de width dentro de la instrucción if para que sea SÓLO string . Esto permite al comstackdor permitir width.endsWith(...) que no permitiría si el tipo fuera string | number string | number .

Puede llamar al typeguard lo que quiera isNotNumber , isNumber , isString , isNotString pero creo que isString es un poco ambiguo y difícil de leer.

En mi aplicación, solo permitimos AZ AZ y de 0 a 9 caracteres. Encontré la respuesta anterior usando ” string % 1 === 0″, a menos que la cadena comenzara con 0xnn (como 0x10) y luego la devolviera como numérica cuando no lo queríamos. La siguiente trampa simple en mi verificación numérica parece ser el truco en nuestros casos específicos.

 function isStringNumeric(str_input){ //concat a temporary 1 during the modulus to keep a beginning hex switch combination from messing us up //very simple and as long as special characters (non az AZ 0-9) are trapped it is fine return '1'.concat(str_input) % 1 === 0;} 

Advertencia : Esto podría estar explotando un error de larga data en Javascript y Actionscript [Number (“1” + the_string)% 1 === 0)], no puedo hablar por eso, pero es exactamente lo que necesitábamos.

Mi solución:

 // returns true for positive ints; // no scientific notation, hexadecimals or floating point dots var isPositiveInt = function(str) { var result = true, chr; for (var i = 0, n = str.length; i < n; i++) { chr = str.charAt(i); if ((chr < "0" || chr > "9") && chr != ",") { //not digit or thousands separator result = false; break; }; if (i == 0 && (chr == "0" || chr == ",")) { //should not start with 0 or , result = false; break; }; }; return result; }; 

Puede agregar condiciones adicionales dentro del ciclo, para ajustarse a sus necesidades particulares.

Puede hacer uso de tipos, como con la biblioteca de flujo y, para obtener la comprobación del tiempo de comstackción estática. Por supuesto, no es terriblemente útil para la entrada del usuario.

 // @flow function acceptsNumber(value: number) { // ... } acceptsNumber(42); // Works! acceptsNumber(3.14); // Works! acceptsNumber(NaN); // Works! acceptsNumber(Infinity); // Works! acceptsNumber("foo"); // Error! 

Aquí hay una línea para verificar si sNum es un valor numérico válido; ha sido probado para una amplia variedad de entradas:

 !isNaN(+s.replace(/\s|\$/g, '')); // returns True if numeric value 

Lo hago así:

 function isString(value) { return value.length !== undefined; } function isNumber(value) { return value.NaN !== undefined; } 

Por supuesto, isString () se disparará aquí si pasa algún otro objeto que tenga definida ‘longitud’.