jquery的$.type()方法和javascript的toString 方法以及Object.prototype.toString.call(),判斷數據類型

判斷數據類型的方式:

1. Object.prototype.toString

對象原型上的toString方法,在對象的this屬性上有可以判斷數據類型的隱藏屬性[[class]],其他的數據類型都有自己的toString方法,但是他們的toString方法被重寫了跟Object.prototype.toString不一樣。

比如:

(1)定義一個變量a是一個數字:var a = 1;

(2)a的類型:typeof a == "number";

(3)a調用toString方法:a.toString() == "1";

(4)爲什麼a是一個數字也可以調用toString方法呢?因爲:a.constructor ==  ƒ Number() { [native code] }; a 是由構造函數Number()new出來的;既然是構造函數構造出來,其實也可以看做是一個特殊的對象

(5)a的原型上是有toString方法,不過這個方法是重寫的,跟Object.prototype.toString的方法不一樣了。同樣的,數組、對象、布爾值等都重寫了toString方法

原型上包含了所有的方法,可以通過__proto__來查看這些方法,從而使用這些方法。

數組原型上也是:

注意:length: 0是原型的length屬性的值,arr有自己的length屬性,有自己的值。 

 (6)分別來看一下,不同類型的數據調用toString方法後的結果:

對象:

數組:

布爾值:

(7)除了對象調用toString方法得到的值判斷數據類型,其他的都是轉換爲字符串,當然,每個類型的toString實現的方式也是不同,比如:數組就是每一項都會調用toString方法,而得到的字符串。

(8)根據上面的變量a,可以調用toString方法,因爲構造函數內的this對象有一個 [[Class]] 隱藏的屬性(internal property),該屬性的值就是類型:

內部屬性 描述
[[Class]] 一個字符串值,表明了該對象的類型.

只有最原始的對象的原型上的toString方法具有[[Class]]屬性,而該屬性正是來區分數據類型的,其他toString方法都被重寫了,失去了判斷類型的功能;正因爲如此,我們通過call來改變this指向,進而使得Object.prototype.toString.call()可以避開自己的toString方法,而去調用原型上的toString方法,才能確定數據類型。

(9)在toString方法被調用時,會執行下面的操作步驟:

 獲取this對象的[[Class]]屬性的值.

計算出三個字符串"[object ", [[Class]]屬性的值, 以及 "]"連接後的新字符串.

 返回計算的的結果

(10)在ES3中,規範文檔並沒有總結出[[class]]內部屬性一共有幾種,不過我們可以自己統計一下,原生對象的[[class]]內部屬性的值一共有10種.分別是:"Array", "Boolean", "Date", "Error", "Function", "Math", "Number", "Object", "RegExp", "String".

(11)ECMAScript 5,對象的[[Class]]屬性的值可以是除了"Arguments", "Array", "Boolean", "Date", "Error", "Function", "JSON", "Math", "Number", "Object", "RegExp", "String"之外的的任何字符串. 

ES5的Object.prototype.toString ( )

在toString方法被調用時,會執行下面的操作步驟:

如果this的值爲undefined,則返回"[object Undefined]".

如果this的值爲null,則返回"[object Null]".

讓O成爲調用ToObject(this)的結果.

讓class成爲O的內部屬性[[Class]]的值.

返回三個字符串"[object ", class, 以及 "]"連接後的新字符串.

(12)Arguments類型

function func(a,b,c){
            console.log(arguments);
            console.log(Object.prototype.toString.call(arguments));
        }
        func(1,2,3);

結果:Arguments(3) [1, 2, 3, callee: ƒ, Symbol(Symbol.iterator): ƒ]
           [object Arguments] 

 

2. 如果能明白toString方法的原理,還可以這麼寫:

var obj = {};
obj.toString.call([])
//結果
"[object Array]"

參考:

JavaScript中Object.prototype.toString方法的原理

jQuery.type()

發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章