今天的学习任务是如何检测一个数据是不是数组?
JavaScript中有基础数据类型和**类型。有Boolean,Number,String,Undefined,Function,和Object,6种数据类型。
我们可以通过typeof检测数据类型:
console.log(typeof function(){return;}) //function
console.log(typeof 'a'); //string
console.log(typeof 123); //number
console.log(typeof a); //undefined
console.log(typeof true); //boolean
console.log(typeof NaN); //number
console.log(typeof !NaN); //boolean
console.log(typeof {name:'lee'}); //object
console.log(typeof ["lee"]); //object
console.log(typeof null); //object
我们可以通过typeof检测大部分数据类型,但{name:’lee’}和[‘lee’]都为object,此时如何区分数组还是对象?
ECMAScript 5 的 isArray函数
function isArray(obj){
return Array.isArray(obj);
}
var arr=["lee","leewr"];
isArray(arr);//true
ECMAScript 5 还有着非常大的兼容性,所以我们并不能完美的使用原生判断,当使用ie8的时候就会出现问题。
所以对构造函数进行检测来判断数据类型。
constructor
constructor属性返回对创建此对象的函数的引用,使用此属性可以检测数组类型。
var test=new array();
if(test.constructor===Array){
console.log('array');
}
instanceOf
除了使用constructor自身属性之外,还可以使用instanceof。
instanceof用来判断某个构造函数的<code>prototype</code>是否存在于被检测对象的原型链里。也就是判断前面的对象是否是后者对象的类或者实例。
var str=["lee","leewr"];
console.log(str instanceof Array)
javascript语言精粹中:
var is_Array=function(value){
return value&&
typeof value==='object'
&& value.constructor===Array
}
需要注意的是,当在不同的window或iframe里构造的数组时会失败。这是因为每一个iframe都有它自己的执行环境,彼此之间并不共享原型链,所以此时的判断一个对象是否为数组就会失败。此时我们有一个更好的方式去判断一个对象是否为数组。
Object.prototype.toString
var is_Array=function(value){
return Object.prototype.toString.call(value) === '[object Array]';
}
使用Object.prototype.toString方法来检测对象类型。toString将返回[object type] type为对象类型。下面是对象检测显示的结果。
function dd(){}
var toString = Object.prototype.toString;
console.log(toString.call(dd));//[object Function]
console.log(toString.call(new Object));//[object Object]
console.log(toString.call(new Array));//[object Array]
console.log(toString.call(new Date));//[object Date]
console.log(toString.call(new String));//[object String]
console.log(toString.call(Math));//[object Math]
console.log(toString.call(undefined));//[object Undefined]
console.log(toString.call(null));//[object Null]
因此我们可以利用对象的Object.prototype.toString方法检测对象是否为数组。在frame下也通过。
最佳检测
最佳检测方法就是,不管原生isArray是否可用,都回归到object.prototype.toString的检测上。
var is_Array=(function(obj){
if(Array.isArray){
return Array.isArray(obj)
}else{
var objectToStringFn =Object.prototype.toString,
arrayToStringResult=othertoString.call([]);
return function(subject){
return objectToStringFn.call(subject)===arrayToStringResult;
}
}
})()
总结
1.typeof不能用于数组检测。
2.instanceof 和 constructor 能够用于数组检测,但是在iframe中会出现问题。
3.对象toString检测数组。
4.最后采用ECMScript5 isArray判断来检测,不支持的采用toString方法来检测。
最后不得不说,javascript语言精粹这本书本不错。小小的一段都有很多需要总结的。