检查JavaScript中变量是数字还是字符串


Answers:


442

如果你处理的文字符号,而不是构造函数,你可以使用typeof运算

typeof "Hello World"; // string
typeof 123;           // number

如果您是通过构造函数创建数字和字符串,比如var foo = new String("foo"),你应该记住,typeof可能会返回objectfoo

检查类型的更简单的方法可能是利用underscore.js中的方法(可在此处找到带注释的源代码),

var toString = Object.prototype.toString;

_.isString = function (obj) {
  return toString.call(obj) == '[object String]';
}

这将返回以下布尔值true

_.isString("Jonathan"); // true
_.isString(new String("Jonathan")); // true

69
其中分别说“字符串”和“数字”
Thilo

27
这是不对的!字符串有两种可能的表示形式。alert(typeof new String())将输出“对象”。更糟糕的是,出于优化目的,JavaScript偶尔会在幕后的两种表示方式之间来回转换
George Mauer,

3
@George根据OP,将仅测试现有变量。
桑普森

3
当然可以,但是说我有函数isString(str){return typeof str ==='string'}某些Java转换可以使用我的方法,因此var myString = new String("stuff I like"); isString(myString)返回false。另外,我不确定背景转换的持续时间,我知道当我调用“ hi” .length时,“ hi”会转换为对象,不确定它会转换多久或是否绑定了到变量。
乔治·莫尔

8
是的,但是您仍然想使用String对象吗?
费利克斯Saparelli

211

最好的方法是使用isNaN+类型转换:

更新了全包方法:

function isNumber(n) { return !isNaN(parseFloat(n)) && !isNaN(n - 0) }

使用正则表达式相同:

function isNumber(n) { return /^-?[\d.]+(?:e-?\d+)?$/.test(n); } 

------------------------

isNumber('123'); // true  
isNumber('123abc'); // false  
isNumber(5); // true  
isNumber('q345'); // false
isNumber(null); // false
isNumber(undefined); // false
isNumber(false); // false
isNumber('   '); // false

21
如果您要对解析为有效数字的字符串进行计数,这似乎是一个不错的解决方案。
Trevor Burnham

2
仅供参考:null强制为0,并返回trueisNumber(null);
爱德华

1
有什么问题function is_number(n) { return /^-?[\d.]+(?:e-?\d+)?$/.test(n);}
OneOfOne 2013年

1
对于诸如“ 123abc”的字符串,此操作也会失败。
灰烬

1
@ash谢谢,我也更新了解决方案以涵盖这种情况。
BitOfUniverse

73

我发现最好的方法是检查字符串中的方法,即:

if (x.substring) {
// do string thing
} else{
// do other thing
}

或者,如果您想对数字属性进行数字检查,

if (x.toFixed) {
// do number thing
} else {
// do other thing
}

这有点像“鸭子打字”,这取决于您哪种方式才最有意义。我没有足够的业力来评论,但是对于装箱的字符串和数字,typeof失败,即:

alert(typeof new String('Hello World'));
alert(typeof new Number(5));

将提醒“对象”。


2
我发现typeof它比总是可以测试字符串(原始或String对象)更好。您只需要测试一种所需类型唯一的方法即可。
ADTC'4

从必须维护代码的人的角度来看,选择此路径可能会造成混淆。“为什么他们使用子字符串而不传递任何值?我在这里缺少什么业务逻辑?” 至少,这需要与解释所涉及逻辑的注释配对。
Lemmings

3
@ Lemmings19实际上并没有调用substring方法,它仅检查x是否具有substring方法。
Alokito

1
我喜欢这种鸭子打字的想法,但是对于类似的事情会失败{substring:"hello"}。我知道,出于我的目的,我只是测试了我需要检查的特定操作(模数)对我需要检查的类型(在字符串模量返回未定义)之后进行的操作,然后检查了该操作而不是获取它的类型。
塔德格·麦当劳-詹森

30

您正在寻找isNaN()

console.log(!isNaN(123));
console.log(!isNaN(-1.23));
console.log(!isNaN(5-2));
console.log(!isNaN(0));
console.log(!isNaN("0"));
console.log(!isNaN("2"));
console.log(!isNaN("Hello"));
console.log(!isNaN("2005/12/12"));

请参见MDN上的JavaScript isNaN()函数


3
我为他们选择方法名称的逆运算感到奇怪。调用isNumber()似乎更直观。
内森·泰勒

12
它实际上不是'isNumber'的逆运算。NaN是javascript中number的特殊值。isNaN将提供给它的所有内容都转换为数字,并检查结果是否为NaN。对于“ 25”之类的字符串,您得到的结果不正确。
Chetan Sastry,2009年

1
我只是用“ 25”测试,它返回false-就像我期望的那样。
雅各布·加德

2
NaN是IEEE 754标准二进制浮点算术中的一个特殊值,而不仅仅是JavaScript。(好吧,确切地说:“ ECMAScript中将IEEE标准的9007199254740990(即(2 ^ 53)-2)不同的“非数字”值表示为单个特殊的NaN值。))
NickFitz

2
请记住,isNaN返回falsenull(但trueundefined)。
托尼

28

检查值是字符串文字还是String对象:

function isString(o) {
    return typeof o == "string" || (typeof o == "object" && o.constructor === String);
}

单元测试:

function assertTrue(value, message) {
    if (!value) {
        alert("Assertion error: " + message);
    }
}

function assertFalse(value, message)
{
    assertTrue(!value, message);
}

assertTrue(isString("string literal"), "number literal");
assertTrue(isString(new String("String object")), "String object");
assertFalse(isString(1), "number literal");
assertFalse(isString(true), "boolean literal");
assertFalse(isString({}), "object");

检查数字类似:

function isNumber(o) {
    return typeof o == "number" || (typeof o == "object" && o.constructor === Number);
}

1
(o.constructor === String)本身就足够了,即使对于字符串文字也是如此。
克里斯·诺

2
如果o === null
TJ,

3
我喜欢这个解决方案。为避免出现空值情况,请避免使用o [“ constructor”]而不是o.constructor
dreamerkumar

2
@VishalKumar所以这是一个所有的需求:function is (type, value) { return value["constructor"] === type; }
ceving

22

从ES2015开始,检查变量是否包含有效数字的正确方法是 Number.isFinite(value)

例子:

Number.isFinite(Infinity)   // false
Number.isFinite(NaN)        // false
Number.isFinite(-Infinity)  // false

Number.isFinite(0)          // true
Number.isFinite(2e64)       // true

Number.isFinite('0')        // false
Number.isFinite(null)       // false


1
不适用于String,这是原始问题。
Eric Grange

18

尝试这个,

<script>
var regInteger = /^-?\d+$/;

function isInteger( str ) {    
    return regInteger.test( str );
}

if(isInteger("1a11")) {
   console.log( 'Integer' );
} else {
   console.log( 'Non Integer' );
}
</script>

尝试“ -2”。它返回false。
KChen

1
为什么您保留(或不编辑)无效的答案?...请注意,负数也可以是整数。
艾森

13

最佳方法是:

function isNumber(num) {
  return (typeof num == 'string' || typeof num == 'number') && !isNaN(num - 0) && num !== '';
};

这满足以下测试用例:

assertEquals("ISNUMBER-True: 0", true, isNumber(0));
assertEquals("ISNUMBER-True: 1", true, isNumber(-1));
assertEquals("ISNUMBER-True: 2", true, isNumber(-500));
assertEquals("ISNUMBER-True: 3", true, isNumber(15000));
assertEquals("ISNUMBER-True: 4", true, isNumber(0.35));
assertEquals("ISNUMBER-True: 5", true, isNumber(-10.35));
assertEquals("ISNUMBER-True: 6", true, isNumber(2.534e25));
assertEquals("ISNUMBER-True: 7", true, isNumber('2.534e25'));
assertEquals("ISNUMBER-True: 8", true, isNumber('52334'));
assertEquals("ISNUMBER-True: 9", true, isNumber('-234'));

assertEquals("ISNUMBER-False: 0", false, isNumber(NaN));
assertEquals("ISNUMBER-False: 1", false, isNumber({}));
assertEquals("ISNUMBER-False: 2", false, isNumber([]));
assertEquals("ISNUMBER-False: 3", false, isNumber(''));
assertEquals("ISNUMBER-False: 4", false, isNumber('one'));
assertEquals("ISNUMBER-False: 5", false, isNumber(true));
assertEquals("ISNUMBER-False: 6", false, isNumber(false));
assertEquals("ISNUMBER-False: 7", false, isNumber());
assertEquals("ISNUMBER-False: 8", false, isNumber(undefined));
assertEquals("ISNUMBER-False: 9", false, isNumber(null));

13
//testing data types accurately in JavaScript (opposed to "typeof")
//from http://bonsaiden.github.com/JavaScript-Garden/
function is(type, obj) {
    var clas = Object.prototype.toString.call(obj).slice(8, -1);
    return obj !== undefined && obj !== null && clas === type;
}

//basic usage
is('String', 'test'); // true
is('Array', true); // false

或修改它以返回未知类型:

function realTypeOf(obj) {
    return Object.prototype.toString.call(obj).slice(8, -1);
}

//usage
realTypeOf(999); // 'Number'

2012年5月12日更新:Javascript的 完整示例:更好的typeof


在以下方面仍有改进的余地realTypeOfrealTypeOf(NaN) -> "Number"这与typeof商定的行为相同,但仍不理想。
2012年

9

这是一种基于以下想法的方法:通过添加零或空字符串将输入强制为数字或字符串,然后进行类型相等性比较。

function is_number(x) { return x === x+0;  }
function is_string(x) { return x === x+""; }

由于某些不可思议的原因,x===x+0似乎效果优于x===+x

是否有任何失败的情况?

同样:

function is_boolean(x) { return x === !!x; }

这似乎比x===true || x===false或略慢typeof x==="boolean"(并且比快得多x===Boolean(x))。

然后还有

function is_regexp(x)  { return x === RegExp(x); }

所有这些都取决于每种类型所特有的“标识”操作的存在,该操作可以应用于任何值并可靠地产生所讨论类型的值。我无法想到这样的日期操作。

对于NaN,有

function is_nan(x) { return x !== x;}

这基本上是下划线的版本,因为它代表约比快四倍isNaN(),但在下划线源提到,“南是唯一的评论数量不等于本身”,并增加了对_.isNumber检查。为什么?还有哪些其他对象不等于自己?另外,下划线使用- x !== +x但是+这里有什么不同?

然后对于偏执狂:

function is_undefined(x) { return x===[][0]; }

或这个

function is_undefined(x) { return x===void(0); }

1
x!== + x首先尝试将x转换为数字。
Adrian Bartholomew 2014年

8

您可以将其除以1吗?

我认为问题将是类似“ 123ABG”的字符串输入

var Check = "123ABG"

if(Check == Check / 1)
{
alert("This IS a number \n")
}

else
{
alert("This is NOT a number \n")
}

这是我最近做的一种方式。


我不认为他希望它是一串数字来返回true。也许使用===
Curtis

7

嗯,怎么样:

function IsString(obj) {
    return obj !== undefined && obj != null && obj.toLowerCase !== undefined;
}

经过几个月的进一步审查后,这仅保证obj是已toLowerCase定义方法或属性名称的对象。我为自己的回答感到ham愧。请参阅票数最高的typeof一个。


7

或仅使用以下内容的倒数isNaN()

if(!isNaN(data))
  do something with the number
else
  it is a string

是的,使用jQuery $.isNumeric()更有趣。


isNaN('123')给出false,尽管参数是数字字符串而不是数字类型
JustAMartin

6

我认为将var转换为字符串会降低性能,至少在最新的浏览器中执行的此测试表明如此。

因此,如果您关心性能,我会使用:

typeof str === "string" || str instanceof String

用于检查变量是否为字符串(即使您使用var str = new String("foo")str instanceof String也将返回true)。

至于检查,如果它是一个数字我会去的原生:isNaN; 功能。


5

jQuery使用以下代码:

function isNumber(obj) {
  return !isNaN( parseFloat( obj ) ) && isFinite( obj );
}

4

此解决方案解决了这里提出的许多问题!

到目前为止,这是我迄今为止使用的最可靠的方法。我没有发明它,也无法回忆起最初发现它的地方。但是它在其他技术失败的地方起作用:

// Begin public utility /getVarType/
// Returns 'Function', 'Object', 'Array',
// 'String', 'Number', 'Boolean', or 'Undefined'
getVarType = function ( data ){
  if (undefined === data ){ return 'Undefined'; }
  if (data === null ){ return 'Null'; }
  return {}.toString.call(data).slice(8, -1);
};  
// End public utility /getVarType/

正确性的例子

var str = new String();
console.warn( getVarType(str) ); // Reports "String"    
console.warn( typeof str );      // Reports "object"

var num = new Number();
console.warn( getVarType(num) ); // Reports "Number"
console.warn( typeof num );      // Reports "object"

var list = [];
console.warn( getVarType( list ) ); // Reports "Array"
console.warn( typeof list );        // Reports "object"

2
而且真的很慢。

Tarazaburo,我不知道您从哪里获得数据,但是为了进行一些基准测试是
必要的

我没有发现这“真的很慢”。测试超过一百万次迭代的速度,我发现它不比typeofChrome 上本机方法的速度(0.788s对1.481s)差一半。考虑到改进的结果,这当然是可以接受的性能。您为什么认为它“真的很慢”?也许是-在IE6 / 7/8中?但是在那些浏览器中,一切都“真的很慢”。
Michael Mikowski 2013年

好吧,我这么说是因为我已经完成了基准测试。再次jsperf.com/check-typeof-number-again上放一个新的小东西typeof速度快100倍,我还缺少什么?

您错过了以下事实:检查类型时,大多数代码都不会发送3m ops / s。无论如何我都不会称其为“真的很慢”。我的基准看起来像这样:var i,k,start = + new Date(); 对于(i = 0; i <1000000; i ++){k = typeof('foo'); k = typeof(123.5); }; end = + new Date(); console.log(结束-开始);
Michael Mikowski


4

在大多数情况下,typeof对我来说效果很好。您可以尝试使用if语句

if(typeof x === 'string' || typeof x === 'number') {
    console.log("Your statement");
}

其中x是您选择的任何变量名


这个答案加上最受好评的答案是什么?
Bartek Banachewicz'3

2
简单明了?
蒂姆·埃里克森

3

我发现的最好的方法也考虑了正数和负数,来自: O'Reilly Javascript和DHTML Cookbook

function isNumber(elem) {
var str = elem.value;
var oneDecimal = false;
var oneChar = 0;
// make sure value hasn't cast to a number data type
str = str.toString( );
for (var i = 0; i < str.length; i++) {
    oneChar = str.charAt(i).charCodeAt(0);
    // OK for minus sign as first character
    if (oneChar =  = 45) {
        if (i =  = 0) {
            continue;
        } else {
            alert("Only the first character may be a minus sign.");
            return false;
        }
    }
    // OK for one decimal point
    if (oneChar =  = 46) {
        if (!oneDecimal) {
            oneDecimal = true;
            continue;
        } else {
            alert("Only one decimal is allowed in a number.");
            return false;
        }
    }
    // characters outside of 0 through 9 not OK
    if (oneChar < 48 || oneChar > 57) {
        alert("Enter only numbers into the field.");
        return false;
    }
}
return true;

}


3

嗯?只需使用正则表达式即可!:)

function isInteger(val) {
  return val.match(/^[0-9]$/)
}

function isFloat(val) {
  return val.match(/^[0-9]*/\.[0-9]+$/)
}

3

因为带有typeof的字符串'1234'将显示'string',并且永远不会发生相反的情况(typeof 123始终是数字),所以最好使用简单的regex /^\-?\d+$/.test(var)。或更先进的匹配浮点数,整数和负数的方法,/^[\-\+]?[\d]+\.?(\d+)?$/ 其重要方面.test是,如果var不是字符串,则不会抛出异常,该值可以是任何值。

var val, regex = /^[\-\+]?[\d]+\.?(\d+)?$/;

regex.test(val)       // false 
val = '1234';
regex.test(val)       // true
val = '-213';
regex.test(val)       // true
val = '-213.2312';
regex.test(val)       // true
val = '+213.2312';
regex.test(val)       // true
val = 123;
regex.test(val)       // true
val = new Number(123);
regex.test(val)       // true
val = new String('123');
regex.test(val)       // true
val = '1234e';
regex.test(val)       // false 
val = {};
regex.test(val)       // false 
val = false;
regex.test(val)       // false 
regex.test(undefined) // false 
regex.test(null)      // false 
regex.test(window)    // false 
regex.test(document)  // false 

如果您正在寻找实型,那么单独使用typeof就可以了。


3

@BitOfUniverse的答案很好,我想出了一种新方法:

function isNum(n) {
    return !isNaN(n/0);
}

isNum('')  // false
isNum(2)   // true
isNum('2k') // false
isNum('2')  //true

我知道0不能算是红利,但是在这里该功能可以完美地工作。


2

类型检查

您可以使用typeof运算符检查变量的类型:

typeof variable

价值检查

下面的代码对数字返回true,对其他任何东西返回false:

!isNaN(+variable);

var variable ='123'; console.log(!isNaN(+ variable)); 尽管为字符串而不是数字类型,但为true
JustAMartin

因为“ 123”是数字!如果您想知道变量的类型,可以轻松使用typeofoperator!@JustAMartin
Amir Fo

是的,但是最初的问题是将字符串类型的变量与数字类型的变量区分开。'123`仍然是字符串。如果我通过123,答案应该是,number但是如果我通过'123'或'abc'或任何其他带引号的文字,则它是一个字符串,并且可以将其解析为数字也无关紧要。
JustAMartin

@JustAMartin好吧,我编辑了答案。
阿米尔·佛

1

XOR操作可用于检测数字或字符串。 number ^ 0将始终给出数字作为输出,而字符串^ 0将始终给出0作为输出。

Example: 
   1)  2 ^ 0 = 2
   2)  '2' ^ 0  = 2
   3)  'Str' ^ 0 = 0

1

简单而彻底:

function isNumber(x) {
  return parseFloat(x) == x
};

测试用例:

console.log('***TRUE CASES***');
console.log(isNumber(0));
console.log(isNumber(-1));
console.log(isNumber(-500));
console.log(isNumber(15000));
console.log(isNumber(0.35));
console.log(isNumber(-10.35));
console.log(isNumber(2.534e25));
console.log(isNumber('2.534e25'));
console.log(isNumber('52334'));
console.log(isNumber('-234'));
console.log(isNumber(Infinity));
console.log(isNumber(-Infinity));
console.log(isNumber('Infinity'));
console.log(isNumber('-Infinity'));

console.log('***FALSE CASES***');
console.log(isNumber(NaN));
console.log(isNumber({}));
console.log(isNumber([]));
console.log(isNumber(''));
console.log(isNumber('one'));
console.log(isNumber(true));
console.log(isNumber(false));
console.log(isNumber());
console.log(isNumber(undefined));
console.log(isNumber(null));
console.log(isNumber('-234aa'));

0

只需使用

myVar.constructor == String

要么

myVar.constructor == Number

如果要处理定义为对象或文字的字符串并进行保存,则不想使用辅助函数。


0
function IsNumeric(num) {
    return ((num >=0 || num < 0)&& (parseInt(num)==num) );
}

0

晚会很晚;但是,当我想检查某些输入是字符串还是数字时,以下内容对我来说一直很有效。

return !!Object.prototype.toString.call(input).match(/\[object (String|Number)\]/);

0

在检查变量是否为数字时创建了一个jsperf。很有趣!typeof实际上具有性能用途。使用typeof用于数字以外的任何东西,通常变为1/3的速度为variable.constructor因为在javascript对象是多数的数据类型; 数字不是!

http://jsperf.com/jemiloii-fastest-method-to-check-if-type-is-a-number

typeof variable === 'number'| 最快的 如果您想要一个数字,例如5,而不是'5'
typeof parseFloat(variable) === 'number'| 最快的 如果您想要一个数字,例如5和'5'

isNaN()较慢,但不会慢很多。我对parseInt和寄予厚望parseFloat,但是他们的速度慢得多。


0

为了检测数字,以下来自JavaScript的段落:Douglas Crockford的The Good Parts是相关的:

isFinite函数是确定某个值是否可以用作数字的最佳方法,因为它拒绝NaN和Infinity。不幸的是,isFinite会尝试将其操作数转换为数字,因此,如果值实际上不是数字,则不是一个很好的测试。您可能需要定义自己的isNumber函数:

var isNumber = function isNumber(value) { return typeof value === 'number' &&
            isFinite(value);
};
By using our site, you acknowledge that you have read and understand our Cookie Policy and Privacy Policy.
Licensed under cc by-sa 3.0 with attribution required.