jQuery靜態方法type使用和源碼分析
jQuery.type方法是檢測資料類型的工具方法,在分析其用法之前先總結下js給我們提供了那些監測資料類型的方法; 一、typeof 操作符 下面是測試代碼 var data=[],a='123',b=0,c=true,d={1:23},e=[123],f=function(){},g=null,h=undefined,i=Math,j=/$.+^/,k= new Date();data.push(a,b,c,d,e,f,g,h,i,j,k); for(var key=0;key<data.length;key++){ console.log(data[key]+'的資料類型是'+typeof data[key]);}在上面的代碼中我盡量列舉了js不同的資料類型和對象,執行結果如下:
//123的資料類型是string// 0的資料類型是number// true的資料類型是boolean//[object Object]的資料類型是object//123的資料類型是object// function (){}的資料類型是function//undefined的資料類型是undefined// [object Math]的資料類型是object// /$.+^/的資料類型是object// Wed Jul 22 2015 15:47:25 GMT+0800 (中國標準時間)的資料類型是object
我們可以看到typeof能檢測到js的6大基本類型中的5個,即String,Boolean,Number,Undefined,Object 其中null被歸為了Object把Function單獨拿了出來,基本上還是能完成任務的,但那是對於複合類型而言就無法進一步區分了,比如到底是數組還是對象呢?這個時候就可以利用另外一個操作符instanceOf了 二、instanceOf操作符 同樣的寫一段測試代碼
var data=[],a='123',b=0,c=true,d={1:23},e=[123],f=function(){},g=null,h=undefined,i=Math,j=/$.+^/,k= new Date();data.push(a,b,c,d,e,f,g,h,i,j,k);console.log(a instanceof String);console.log(b instanceof Number);console.log(c instanceof Boolean);console.log(d instanceof Object);console.log(e instanceof Array);console.log(f instanceof Function);console.log(j instanceof RegExp);console.log(k instanceof Date);
在瀏覽器中的運行結果如下:
// false// false// true// true// true// true// true
可以看到只有複合類型的結果為真,而且必須保證類型是一一對應的,顯然這個方法只能做個一檢驗方法存在,並不能在我們不知道具體資料類型的時候去做判斷,可以作為typeof的一個輔助測試手段 三、constructor屬性 同樣的先寫下測試代碼
var data=[],a='123',b=0,c=true,d={1:23},e=[123],f=function(){},g=null,h=undefined,i=Math,j=/$.+^/,k= new Date(); data.push(a,b,c,d,e,f,g,h,i,j,k); for(var key=0;key<data.length;key++){ try{ console.log(data[key]+'的檢測結果是' +data[key].constructor); }catch(e){ } }
運行結果如下:
//123的檢測結果是function String() { [native code] }//0的檢測結果是function Number() { [native code] }//true的檢測結果是function Boolean() { [native code] }//[object Object]的檢測結果是function Object() { [native code] }//123的檢測結果是function Array() { [native code] }//function (){}的檢測結果是function Function() { [native code] }//[object Math]的檢測結果是function Object() { [native code] }///$.+^/的檢測結果是function RegExp() { [native code] }//Wed Jul 22 2015 16:23:41 GMT+0800 (中國標準時間)的檢測結果是function Date() { [native code] }
其中null調用是會報錯所以加了try語句,相對而言此方法能夠很方便的擷取其建構函式,這樣就能判斷了,遺憾的是該屬性並非是唯讀屬性是可以被修改的,一旦被修改或者涉及到對象繼承等問題時會導致不準而且在遇到某些值得時候會報錯導致程式無法運行比如null,還有沒有其他方法呢? 四、Object.prototype.toString方法 該方法通過調用待測試資料的toString方法來獲得其建構函式的字串表示,測試代碼如下: var data=[],a='123',b=0,c=true,d={1:23},e=[123],f=function(){},g=null,h=undefined,i=Math,j=/$.+^/,k= new Date(); data.push(a,b,c,d,e,f,g,h,i,j,k); for(var key=0;key<data.length;key++){ console.log(data[key]+'的檢測結果是' +Object.prototype.toString.call(data[key])); }運行結果如下:
//123的檢測結果是[object String]//0的檢測結果是[object Number]//true的檢測結果是[object Boolean]//[object Object]的檢測結果是[object Object]//123的檢測結果是[object Array]//function (){}的檢測結果是[object Function]//null的檢測結果是[object Null]//undefined的檢測結果是[object Undefined]//[object Math]的檢測結果是[object Math]///$.+^/的檢測結果是[object RegExp]//Wed Jul 22 2015 16:33:05 GMT+0800 (中國標準時間)的檢/測結果是[object Date]
看到結果是不是感覺很爽!不僅可以檢測到所有資料類型,而且把Object子類型也現實了出來,也不用擔心報錯,之所以能實現是因為所有的對象都是基於Object而來的,其實jQery也是採取的這個方法,只不過是做了進一步處理讓我們看著更爽而已! 看看使用jQuery.type的結果 var data=[],a='123',b=0,c=true,d={1:23},e=[123],f=function(){},g=null,h=undefined,i=Math,j=/$.+^/,k= new Date(); data.push(a,b,c,d,e,f,g,h,i,j,k); for(var key=0;key<data.length;key++){ console.log(data[key]+'的檢測結果是' +$.type(data[key])); }運行結果:
//123的檢測結果是string//0的檢測結果是number//的檢測結果是boolean//[object Object]的檢測結果是object//123的檢測結果是array//function (){}的檢測結果是function//null的檢測結果是null//undefined的檢測結果是undefined//[object Math]的檢測結果是object///$.+^/的檢測結果是regexp//Wed Jul 22 2015 16:44:25 GMT+0800 (中國標準時間)的檢測結果是date
ok,結果無可挑剔了,下面附上源碼: type: function( obj ) { return obj == null ? String( obj ) : class2type[ toString.call(obj) ] || "object"; },如果是undefined或者是null他們的資料累類型就是自己,直接返回字串形式,如果是其他資料就執行toString方法,該方法在之前有介紹 toString = Object.prototype.toString,返回的結果就像之前測試過的結果類似 [object Date]這樣的 如果不能取到就返回object,結果作class2type的鍵,下面來看下class2type的定義: // Populate the class2type mapjQuery.each("Boolean Number String Function Array Date RegExp Object".split(" "), function(i, name) { class2type[ "[object " + name + "]" ] = name.toLowerCase();});好了type方法分析完畢。