typeof和instanceof都可以用来判断变量,它们的用法有很大区别
typeof会返回一个变量的基本类型,instanceof返回的是一个布尔值,需要注意的是,instanceof只能用来判断对象和函数,不能用来判断字符串和数字等
先说instanceof
instanceof 运算符用来测试一个对象在其原型链中是否存在一个构造函数的 prototype 属性。
语法
object instanceof constructor
描述
instanceof 运算符用来检测 constructor.prototype 是否存在于参数 object 的原型链上。
理解:object.__proto__ === constructor.prototype ? => boolean
定义构造函数 function C(){} function D(){} var o = new C(); o instanceof C; // true,因为Object.getPrototypeOf(o) === C.prototype // 扩展:可以理解为 o.__proto__ === C.prototype o instanceof D; // false,D.prototype不在o的原型链上 o instaceof Object; // true,Object.prototype.isPrototypeOf(o) 返回true C.prototype instanceof Object // true ,同上 C.prototype = {}; var o2 = new C(); o2 instanceof C; // true o instanceof C; // false,C.prototype指向一个空对象,这个空对象不在o的原型链上 D.prototype = new C(); // 继承 var o3 = new D(); o3 instanceof D; // true o3 instanceof C; // true
如果表达式 obj instanceof Foo 返回true,则并不意味着该表达式会永远返回true,因为Foo.prototype属性的值有可能会改变,改变之后的值很有可能不存在于obj的原型链上,这时原表达式的值就会成为false。另外一种情况下,原表达式的值也会改变,就是改变对象obj的原型链的情况,虽然在目前的ES规范中,我们只能读取对象的原型而不能改变它,但借助于非标准的__proto__魔法属性,是可以实现的。比如执行obj.__proto__ = {}之后,obj instanceof Foo就会返回false了。
String和Date对象同时也属于Object类型
var simpleStr = "some simple string"; var myString = new String(); var newStr = new String("String created with constructor"); var myDate = new Date(); var myObj = {}; simpleStr instanceof String; // false,检查原型链会找到undefined myString instanceof String; // true newStr instanceof String; // true myString instanceof Object; // true myObj instanceof Object; // true ({}) instanceof Object; // true myString instanceof Date; // false myDate instanceof Date; // true myDate instanceof Object; // true myDate instanceof String; // false
typeof
typeof操作符返回一个字符串,指示未经计算的操作数的类型。
最新的 ECMAScript 标准定义了 8 种数据类型:
- 6 种原始类型,使用 typeof 运算符检查:
- null:
typeof instance === "object"
。 - Object:
typeof instance === "object"
。任何 constructed 对象实例的特殊非数据结构类型,也用做数据结构:new Object,new Array,new Map,new Set,new WeakMap,new WeakSet,new Date,和几乎所有通过 new keyword 创建的东西。
记住 typeof
操作符的唯一目的就是检查数据类型,如果我们希望检查任何从 Object 派生出来的结构类型,使用 typeof
是不起作用的,因为总是会得到 "object"
。检查 Object 种类的合适方式是使用 instanceof 关键字。但即使这样也存在误差。
(以上摘自MDN Web Docs)
如果我们想要判断一个变量是否存在,可以使用typeof:(不能使用if(a) 若a未声明,则报错)
if(typeof a != 'undefined'){ //变量存在 }
typeof用于判断数据类型,返回值为6个字符串,分别为string
、Boolean
、number
、function
、object
、undefined
。
var a = [34,4,3,54], b = 34, c = 'adsfas', d = function(){}, e = true, f = null, g; console.log(typeof(a));//object console.log(typeof(b));//number console.log(typeof(c));//string console.log(typeof(d));//function console.log(typeof(e));//boolean console.log(typeof(f));//object console.log(typeof(g));//undefined
typeof
在判断
null
、
array
、
object
以及函数实例
(new + 函数)
时,得到的都是
object
。这使得在判断这些数据类型的时候,得不到真是的数据类型。由此引出
instanceof
。
instanceof
判断该对象是谁的实例,同时我们也就知道instanceof是对象运算符。
这里的实例就牵扯到了对象的继承,它的判断就是根据原型链进行搜寻,在对象obj1的原型链上如果存在另一个对象obj2的原型属性,那么表达式(obj1 instanceof obj2)返回值为true;否则返回false。
- typeof判断所有变量的类型,返回值有number,boolean,string,function,object,undefined。
- typeof对于丰富的对象实例,只能返回"Object"字符串。
- instanceof用来判断对象,代码形式为obj1 instanceof obj2(obj1是否是obj2的实例),obj2必须为对象,否则会报错!其返回值为布尔值。
- instanceof可以对不同的对象实例进行判断,判断方法是根据对象的原型链依次向下查询,如果obj2的原型属性存在obj1的原型链上,(obj1 instanceof obj2)值为true。