为什么instanceof对某些文字返回false?

Jon*_*ski 273 javascript instanceof literals

"foo" instanceof String //=> false
"foo" instanceof Object //=> false
true instanceof Boolean //=> false
true instanceof Object //=> false
false instanceof Boolean //=> false
false instanceof Object //=> false

// the tests against Object really don't make sense
Run Code Online (Sandbox Code Playgroud)

数组文字和对象文字匹配......

[0,1] instanceof Array //=> true
{0:1} instanceof Object //=> true
Run Code Online (Sandbox Code Playgroud)

为什么不是所有人呢?或者,他们为什么呢?
而且,它们是什么样的呢?

在FF3,IE7,Opera和Chrome中也是如此.所以,至少它是一致的.


错过了一些.

12.21 instanceof Number //=> false
/foo/ instanceof RegExp //=> true
Run Code Online (Sandbox Code Playgroud)

Joh*_*kin 397

基元是一种不同于Javascript中创建的对象的类型.来自Mozilla API文档:

var color1 = new String("green");
color1 instanceof String; // returns true
var color2 = "coral";
color2 instanceof String; // returns false (color2 is not a String object)
Run Code Online (Sandbox Code Playgroud)

我找不到用代码构造原始类型的任何方法,也许这是不可能的.这可能是人们使用typeof "foo" === "string"而不是instanceof.

记住这样的事情的一个简单方法就是问自己"我想知道什么是理智和易学"?无论答案是什么,Javascript都会做另一件事.

  • 你的术语是错的."文字"一词​​是指在不使用构造函数的情况下创建数据的语法.它不涉及结果数据.文字语法可用于创建对象和非对象.正确的术语是"基元",它指的是非对象数据.一些数据具有原始和对象表示.String是这些类型的数据之一. (55认同)
  • 可悲的是,一个很好的提示 - "Javascript做另一件事". (36认同)
  • 仅供参考,您可以创建没有文字语法的基元.`(new String()).valueOf();` (14认同)
  • 请注意,`typeof foo ==='string'`是不够的:请参阅axkibe的回答. (11认同)
  • 每天都有一个新的理由来讨厌JavaScript是一个美好的一天.我知道它已经过期但我感谢你的这篇文章. (3认同)
  • 另外,`typeof new String('')`返回`"object"` (2认同)

axk*_*ibe 96

我用:

function isString(s) {
    return typeof(s) === 'string' || s instanceof String;
}
Run Code Online (Sandbox Code Playgroud)

因为在JavaScript中字符串可以是文字或对象.

  • 我发现了一些简短的东西.`function isString(s){return s.constructor === String; 用于文字和字符串对象(至少在V8中) (27认同)
  • 一定要喜欢JavaScript. (7认同)
  • 我使用jQuery.type(s)==='string'(http://api.jquery.com/jquery.type/),jQuery.isArray(),jQuery.isFunction(),jQuery.isNumeric()当它是可能. (2认同)

Aad*_*hah 57

在JavaScript中,一切都是一个对象(或者至少可以被视为一个对象),除了基元(布尔值,空值,数字,字符串和值undefined(以及ES6中的符号)):

console.log(typeof true);           // boolean
console.log(typeof 0);              // number
console.log(typeof "");             // string
console.log(typeof undefined);      // undefined
console.log(typeof null);           // object
console.log(typeof []);             // object
console.log(typeof {});             // object
console.log(typeof function () {}); // function
Run Code Online (Sandbox Code Playgroud)

正如您所见,对象,数组和值null都被视为对象(null是对不存在的对象的引用).区分函数是因为它们是一种特殊类型的可调用对象.但它们仍然是物体.

在另一方面,文字true,0,""undefined不是对象.它们是JavaScript中的原始值.然而,布尔值,数字和字符串也有构造函数Boolean,NumberString分别包装它们各自的基元以提供附加功能:

console.log(typeof new Boolean(true)); // object
console.log(typeof new Number(0));     // object
console.log(typeof new String(""));    // object
Run Code Online (Sandbox Code Playgroud)

正如你可以看到当原始值内的包裹Boolean,NumberString建设者,他们分别成为目标.该instanceof操作仅适用于对象(这就是为什么它返回false的原始值):

console.log(true instanceof Boolean);              // false
console.log(0 instanceof Number);                  // false
console.log("" instanceof String);                 // false
console.log(new Boolean(true) instanceof Boolean); // true
console.log(new Number(0) instanceof Number);      // true
console.log(new String("") instanceof String);     // true
Run Code Online (Sandbox Code Playgroud)

正如您所看到的那样,typeof并且instanceof不足以测试值是否为布尔值,数字或字符串 - typeof仅适用于原始布尔值,数字和字符串; 并且instanceof不适用于原始布尔值,数字和字符串.

幸运的是,这个问题有一个简单的解决方案.默认实现toString(即它本身定义的Object.prototype.toString)返回[[Class]]原始值和对象的内部属性:

function classOf(value) {
    return Object.prototype.toString.call(value);
}

console.log(classOf(true));              // [object Boolean]
console.log(classOf(0));                 // [object Number]
console.log(classOf(""));                // [object String]
console.log(classOf(new Boolean(true))); // [object Boolean]
console.log(classOf(new Number(0)));     // [object Number]
console.log(classOf(new String("")));    // [object String]
Run Code Online (Sandbox Code Playgroud)

[[Class]]值的内部属性比值更有用typeof.我们可以使用如下Object.prototype.toString创建我们自己的(更有用的)typeof运算符版本:

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

console.log(typeOf(true));              // Boolean
console.log(typeOf(0));                 // Number
console.log(typeOf(""));                // String
console.log(typeOf(new Boolean(true))); // Boolean
console.log(typeOf(new Number(0)));     // Number
console.log(typeOf(new String("")));    // String
Run Code Online (Sandbox Code Playgroud)

希望本文有所帮助.要了解有关基元和包装对象之间差异的更多信息,请阅读以下博客文章:JavaScript基元的秘密生活

  • +1,altough`null`也是[原始值](http://es5.github.io/#x4.3.2)(只有`typeof`运算符令人困惑) (6认同)

小智 32

您可以使用构造函数属性:

'foo'.constructor == String // returns true
true.constructor == Boolean // returns true
Run Code Online (Sandbox Code Playgroud)

  • 请注意,在测试变量时,此技术在某些情况下可能会失败.在上面的例子中有一个隐含的引用`String`和`Boolean`前面的当前窗口,所以如果你正在测试在另一个窗口(如弹出窗口或框架)中创建的字符串变量的`constructor`属性,将_not_等于简单的`String`,它将等于`thatOtherWindowsName.String`. (18认同)
  • 如果您传递了String的后代,则会失败. (5认同)

sau*_*795 6

 typeof(text) === 'string' || text instanceof String; 
Run Code Online (Sandbox Code Playgroud)

你可以使用它,它将适用于两种情况

  1. var text="foo"; // typeof会起作用

  2. String text= new String("foo"); // instanceof会起作用