检查变量是否是 JavaScript 中的字符串

声明:本页面是StackOverFlow热门问题的中英对照翻译,遵循CC BY-SA 4.0协议,如果您需要使用它,必须同样遵循CC BY-SA许可,注明原文地址和作者信息,同时你必须将它归于原作者(不是我):StackOverFlow 原文地址: http://stackoverflow.com/questions/4059147/
Warning: these are provided under cc-by-sa 4.0 license. You are free to use/share it, But you must attribute it to the original authors (not me): StackOverFlow

提示:将鼠标放在中文语句上可以显示对应的英文。显示中英文
时间:2020-08-23 07:18:44  来源:igfitidea点击:

Check if a variable is a string in JavaScript

javascript

提问by Olical

How can I determine whether a variable is a string or something else in JavaScript?

如何确定变量是字符串还是 JavaScript 中的其他内容?

采纳答案by Pablo Santa Cruz

You can use typeofoperator:

您可以使用typeof运算符:

var booleanValue = true; 
var numericalValue = 354;
var stringValue = "This is a String";
var stringObject = new String( "This is a String Object" );
alert(typeof booleanValue) // displays "boolean"
alert(typeof numericalValue) // displays "number"
alert(typeof stringValue) // displays "string"
alert(typeof stringObject) // displays "object"

Example from this webpage. (Example was slightly modified though).

来自此网页的示例。(尽管示例略有修改)。

This won't work as expected in the case of strings created with new String(), but this is seldom used and recommended against[1][2]. See the other answers for how to handle these, if you so desire.

在使用 创build 的字符串的情况下,这不会按预期工作new String(),但很少使用,建议不要使用[1][2]。如果您愿意,请参阅其他答案以了解如何处理这些问题。



  1. The Google JavaScript Style Guide says to never use primitive object wrappers.
  2. Douglas Crockford recommended that primitive object wrappers be deprecated.
  1. Google JavaScript Style Guide说永远不要使用原始对象包装器
  2. Douglas Crockford建议弃用原始对象包装器

回答by DRAX

This is what works for me:

这对我有用:

if (typeof myVar === 'string' || myVar instanceof String)
// it's a string
else
// it's something else

回答by Orwellophile

Since 580+ people have voted for an incorrect answer, and 800+ have voted for a working but shotgun-style answer, I thought it might be worth redoing my answer in a simpler form that everybody can understand.

由于 580+ 人投票支持错误答案,800+ 人投票支持有效但霰弹枪式的答案,我认为可能值得以每个人都能理解的更简单的形式重做我的答案。

function isString(x) {
  return Object.prototype.toString.call(x) === "[object String]"
}

Or, inline (I have an UltiSnip setup for this):

或者,内联(我有一个 UltiSnip 设置):

Object.prototype.toString.call(myVar) === "[object String]"

FYI, Pablo Santa Cruz's answer is wrong, because typeof new String("string")is object

仅供参考,Pablo Santa Cruz 的回答是错误的,因为typeof new String("string")object

DRAX's answer is accurate and functional, and should be the correct answer (since Pablo Santa Cruz is most definitely incorrect, and I won't argue against the popular vote.)

DRAX 的回答准确且实用,应该是正确的答案(因为 Pablo Santa Cruz 绝对是错误的,我不会反对大众投票。)

However, this answer is also definitely correct, and actually the best answer (except, perhaps, for the suggestion of using lodash/underscore). disclaimer: I contributed to the lodash 4 codebase.

然而,这个答案也绝对是正确的,实际上是最好的答案(除了建议使用lodash/ underscore)。免责声明:我为 lodash 4 代码库做出了贡献。

My original answer (which obviously flew right over a lot of heads) follows:

我的原始答案(显然是在很多人头上飞过)如下:

I transcoded this from underscore.js:

我从 underscore.js 转码:

['Arguments', 'Function', 'String', 'Number', 'Date', 'RegExp'].forEach( 
    function(name) { 
        window['is' + name] = function(obj) {
              return toString.call(obj) == '[object ' + name + ']';
    }; 
});

That will define isString, isNumber, etc.

这将定义 isString、isNumber 等。



In Node.js, this can be implemented as a module:

在 Node.js 中,这可以作为一个模块来实现:

module.exports = [
  'Arguments',
  'Function', 
  'String', 
  'Number', 
  'Date', 
  'RegExp'
].reduce( (obj, name) => {
  obj[ 'is' + name ] = x => toString.call(x) == '[object ' + name + ']';
  return obj;
}, {});

[edit]: Object.prototype.toString.call(x)works to delineate between functions and async functions as well:

[编辑]:也Object.prototype.toString.call(x)用于描述函数和异步函数:

const fn1 = () => new Promise((resolve, reject) => setTimeout(() => resolve({}), 1000))
const fn2 = async () => ({})

console.log('fn1', Object.prototype.toString.call(fn1))
console.log('fn2', Object.prototype.toString.call(fn2))

回答by ClearCloud8

I recommend using the built-in functions from jQueryor lodash/Underscore. They're simpler to use and easier to read.

我建议使用jQuerylodash/Underscore的内置函数。它们更易于使用且更易于阅读。

Either function will handle the case DRAX mentioned... that is, they bothcheck if (A) the variable is a string literal or (B) it's an instance of the String object. In either case, these functions correctly identify the value as being a string.

两个函数都将处理 DRAX 提到的情况……也就是说,它们检查(A)变量是字符串文字还是(B)它是 String 对象的实例。在任何一种情况下,这些函数都会正确地将该值标识为字符串。

lodash / Underscore.js

lodash / Underscore.js

if(_.isString(myVar))
   //it's a string
else
   //it's something else

jQuery

jQuery

if($.type(myVar) === "string")
   //it's a string
else
   //it's something else

See lodash Documentation for _.isString()for more details.

有关更多详细信息,请参阅_.isString() 的 lodash 文档

See jQuery Documentation for $.type()for more details.

有关更多详细信息,请参阅$.type() 的 jQuery 文档

回答by ling

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

I saw that here:

我在这里看到:

http://perfectionkills.com/instanceof-considered-harmful-or-how-to-write-a-robust-isarray/

http://perfectkills.com/instanceof-thinked-harmful-or-how-to-write-a-robust-isarray/

回答by Cody

Best way:

最好的办法:

var s = 'String';
var a = [1,2,3];
var o = {key: 'val'};

(s.constructor === String) && console.log('its a string');
(a.constructor === Array) && console.log('its an array');
(o.constructor === Object) && console.log('its an object');
(o.constructor === Number || s.constructor === Boolean) && console.log('this won\'t run');

Each of these has been constructed by its appropriate class function, like "new Object()" etc.

其中每一个都由其适当的类函数构造,如“new Object()”等。

Also, Duck-Typing: "If it looks like a duck, walks like a duck, and smells like a duck - it must be an Array" Meaning, check its properties.

另外,Duck-Typing:“如果它看起来像一只鸭子,走路像一只鸭子,闻起来像一只鸭子——它一定是一个数组”意思是,检查它的属性。

Hope this helps.

希望这可以帮助。

Edit; 12/05/2016

编辑; 12/05/2016

Remember, you can always use combinations of approaches too. Here's an example of using an inline mapof actions with typeof:

请记住,您也可以随时使用方法的组合。这是一个使用带有typeof内联操作映射的示例:

var type = { 'number': Math.sqrt.bind(Math), ... }[ typeof datum ];

Here's a more 'real world' example of using inline-maps:

这是使用内联地图的更“真实世界”的示例:

function is(datum) {
    var isnt = !{ null: true, undefined: true, '': true, false: false, 0: false }[ datum ];
    return !isnt;
}
console.log( is(0), is(false), is(undefined), ... );  // >> true true false

This function would use [ custom ] "type-casting" -- rather, "type-/-value-mapping" -- to figure out if a variable actually "exists". Now you can split that nasty hair between null& 0!

该函数将使用 [custom]“类型转换”——而是“类型/值映射”——来确定变量是否确实“存在”。现在你可以在null&之间分割那根讨厌的头发了0

Many times you don't even care about its type. Another way to circumvent typing is combining Duck-Type sets:

很多时候你甚至不关心它的类型。另一种规避打字的方法是结合 Duck-Type 集:

this.id = "998";  // use a number or a string-equivalent
function get(id) {
    if (!id || !id.toString) return;
    if (id.toString() === this.id.toString()) http( id || +this.id );
    // if (+id === +this.id) ...;
}

Both Number.prototypeandString.prototypehave a .toString() method. You just made sure that the string-equivalent of the number was the same, and then you made sure that you passed it into the httpfunction as a Number. In other words, we didn't even carewhat its type was.

两者Number.prototypeString.prototype.toString() method。您只需确保数字的字符串等效项相同,然后确保将其http作为Number. 换句话说,我们甚至不在乎它的类型是什么。

Hope that gives you more to work with :)

希望能给你更多的工作:)

回答by customcommander

I can't honestly see why one would not simply use typeofin this case:

老实说,我不明白为什么typeof在这种情况下不会简单地使用:

if (typeof str === 'string') {
  return 42;
}

Yes it will fail against object-wrapped strings (e.g. new String('foo')) but these are widely regarded as a bad practice and most modern development tools are likely to discourage their use. (If you see one, just fix it!)

是的,它会因对象包装字符串(例如new String('foo'))而失败,但这些被广泛认为是一种不好的做法,大多数现代开发工具可能会阻止它们的使用。(如果你看到一个,只需修复它!)

The Object.prototype.toStringtrick is something that all front-end developers have been found guilty of doing one day in their careers but don't let it fool you by its polish of clever: it will break as soon as something monkey-patch the Object prototype:

Object.prototype.toString诀窍是什么,所有的前端开发人员已经被判有罪在自己的职业生涯有一天会做,但不要让它通过其巧妙抛光欺骗你:这会尽快打破的东西猴子补丁对象的原型:

const isString = thing => Object.prototype.toString.call(thing) === '[object String]';

console.log(isString('foo'));

Object.prototype.toString = () => 42;

console.log(isString('foo'));

回答by ScottyG

I like to use this simple solution:

我喜欢使用这个简单的解决方案:

var myString = "test";
if(myString.constructor === String)
{
     //It's a string
}

回答by Rob Brander

This is a great example of why performance matters:

这是一个很好的例子,说明为什么性能很重要:

Doing something as simple as a test for a string can be expensive if not done correctly.

如果没有正确完成,做一些像测试字符串这样简单的事情可能会很昂贵。

For example, if I wanted to write a function to test if something is a string, I could do it in one of two ways:

例如,如果我想编写一个函数来测试某个东西是否是一个字符串,我可以通过以下两种方式之一来完成:

1) const isString = str => (Object.prototype.toString.call(str) === '[object String]');

1) const isString = str => (Object.prototype.toString.call(str) === '[object String]');

2) const isString = str => ((typeof str === 'string') || (str instanceof String));

2) const isString = str => ((typeof str === 'string') || (str instanceof String));

Both of these are pretty straight forward, so what could possibly impact performance? Generally speaking, function calls can be expensive, especially if you don't know what's happening inside. In the first example, there is a function call to Object's toString method. In the second example, there are no function calls, as typeof and instanceof are operators. Operators are significantly faster than function calls.

这两个都非常简单,那么什么可能会影响性能呢?一般来说,函数调用可能会很昂贵,特别是如果您不知道内部发生了什么。在第一个示例中,有一个对 Object 的 toString 方法的函数调用。在第二个示例中,没有函数调用,因为 typeof 和 instanceof 是运算符。运算符比函数调用快得多。

When the performance is tested, example 1 is 79% slower than example 2!

测试性能时,示例1比示例2慢79%!

See the tests: https://jsperf.com/isstringtype

查看测试:https: //jsperf.com/isstringtype

回答by wheelmaker

if (s && typeof s.valueOf() === "string") {
  // s is a string
}

Works for both string literals let s = 'blah'and for Object Strings let s = new String('blah')

适用于字符串文字let s = 'blah'和对象字符串let s = new String('blah')