本文主要分析Zepto庫的類型判斷函數typeof,使用Zepto版本爲 V.1.6.7。javascript
先來看Zepto中對typeof()函數的實現java
var $, class2type={}, toString = class2type.toString //判斷obj的類型,返回類型字符串 null | undefined | string | number | boolean | object | function | array | regexp | date | error function type(obj){ return obj == null ? String(obj):class2type[toString.call(obj)] || 'object'; } function likeArray(obj){ return typeof(obj.length) == 'number'}//判斷是不是數組類似對象 $.each = function(elements, callback) { var i,key; if(likeArray(elements)){//遍歷數組類似對象 for(i=0;i<elements.length;i++){ if(callback.call(elements[i],i,elements[i]) === false) return elements } }else{//遍歷對象的每一個鍵 for(key in elements) if(callback.call(elements[key],key,elements[key]) === false) return elements } return elements } //將類型存儲入class2type中 $.each("Boolean Number String Function Object Array Date RegExp Error".split(" "),function(i,name){ class2type["[object " + name + "]"] = name.toLowerCase(); })
首先定義了class2type對象,並賦值toString=class2type.toString,實際上toString引用了Object.prototype.toString.jquery
Object.prototype.toString(obj)時object的基礎方法,其功能爲返回對象的字符串表示,可參考如下代碼正則表達式
function Person(name,age,sex){ this.name = name; this.age = age; this .sex = sex; } var p = new Person("Jack",21,"male"); var class2type = {}, toString = class2type.toString; console.log(toString.call(p)) console.log(toString.call(Person)) console.log(toString.call("hello world")) console.log(toString.call(true)) console.log(toString.call(new Array())) console.log(toString.call(null)) console.log(toString.call(1)) console.log(toString.call(undefined)) console.log(toString.call(/^d{3}$/)) console.log(toString.call(new Date())) console.log(toString.call(new Error()))
其返回值爲數組
[object Object] [object Function] [object String] [object Boolean] [object Array] [object Null] [object Number] [object Undefined] [object RegExp] [object Date] [object Error]
能夠看到對於 對象,函數,字符串,布爾值,數組,空類型,數字,未定義,正則表達式,日期,錯誤,Object.prototype.toString()方法都能返回相應的字符串[object Type]函數
Zepto實現了$.each()方法,用於遍歷數組和對象,並對其元素執行定義好的回調函數(使用jquery和zepto的童靴對這個應該都熟)this
$.each(obj)方法的實現思路很簡單,若是參數obj存在length屬性,那麼判斷其爲數組,進行遍歷並調用回調函數,若回調函數返回false,那麼終止後續遍歷。若是參數obj無length屬性,判斷其爲object,並使用for...in遍歷prototype
$.each("Boolean Number String Function Object Array Date RegExp Error".split(" "),function(i,name){ class2type["[object " + name + "]"] = name.toLowerCase(); })
上述函數在class2type對象上構建了各個類型的映射,class2type的值爲code
{ [object Array]:"array", [object Boolean]:"boolean" , [object Date]:"date" , [object Error]:"error", [object Function]:"function" , [object Number]:"number" , [object Object]:"object" , [object RegExp]:"regexp" , [object String]:"string" }
能夠看到class2type對象中未存儲[object Null]和[object Undefined],因此在type()函數中首先使用obj==null判斷了是不是null或者undefined,regexp
若是obj==null爲true,使用String(null)和String(undefined)分別返回null和undefined
若是obj==null爲false, 使用class2type(toString().call(obj))返回class2type中存儲的屬性值
string | number | boolean | object | function | array | regexp | date | error
若是class2type中查找不到的類型,那麼判斷其爲object類型。
綜上所述,Zepto的type()方法可以識別
null | undefined | string | number | boolean | object | function | array | regexp | date | error
共計11種類型。
對比javascript提供的typeof只能識別 number | string | boolean | object | undefined | function 六種類型。
以上!