JavaScript顯式型別轉換與隱式型別轉換
本文談談JavaScript的型別轉換,我們知道在JavaScript中宣告變數不需指定型別, 對變數賦值也沒有型別檢查,同時JavaScript允許隱式型別轉換。這些特徵說明JavaScript屬於弱型別的語言。
在強型別的C++中,多數情況下建構函式需要宣告為explicit
來避免隱式型別轉換引起的誤用
(見Item 15:資源管理類需要提供對原始資源的訪問)。
弱型別的語言中型別的誤用會更加隱蔽,比如:
// 彈出對話方塊中輸入1
var a = prompt('input a number');
var b = a + 1;
console.log(b); // 控制檯輸出 11
本文便來總結一下如何使用JavaScript進行型別轉換,以及JavaScript中隱式型別轉換的規則。
轉換為字串
轉換為字串是應用程式中的常見操作,幾乎所有語言都提供了將任何型別轉換為字串的通用介面。 比如Java和C#的toString
方法、C++的函式std::to_string
,當然還有JavaScript的toString
方法。
多數的JavaScript宿主環境(比如Node.js和Chrome)都提供了全域性函式toString
;
與此同時Object.prototype
也定義了toString
方法,使得所有物件都擁有轉換為字串的能力。
比如一個Number
轉換為String
var n = 1;
n.toString(); // '1'
toString
接受一個引數指定進位制,預設為10.
可以利用這個引數生成包括字母和數字的隨機字串:
Math.random().toString(36).substr(2);
random
生成一個0到1的隨機數,36進位制的字符集為[0-9a-z]
(36個),substr
用來截掉起始的"0."
。
另外Object.prototype.toString
可以用來檢測JavaScript物件的型別:
var toString = Object.prototype.toString;
toString.call(new Date); // [object Date]
toString.call(new String); // [object String]
toString.call(Math); // [object Math]
// Since JavaScript 1.8.5
toString.call(undefined); // [object Undefined]
toString.call(null); // [object Null]
// 自定義型別
toString.call(new MyClass); // [object Object]
轉換為數字
字串轉換為數字也是常見需求,通常用來從使用者輸入或檔案來獲得一個Number
。
在C++中可以用atoi
、cin
、scanf
等函式,在JavaScript中可以直接用parseInt
和parseFloat
。
例如:
var iNum1 = parseInt("12345red"); //返回 12345
var iNum1 = parseInt("0xA"); //返回 10
var iNum1 = parseInt("56.9"); //返回 56
var iNum1 = parseInt("red"); //返回 NaN
var fNum4 = parseFloat("11.22.33"); //返回 11.22
注意NaN
是JavaScript中唯一一個不等於自己的值。(NaN
== NaN) === false
! 如果遇到非法字元,parseInt
和parseFloat
會忽略之後的所有內容。
parseFloat
只接受十進位制數字的字串,而parseInt
還提供了第二個引數(可選)用來指定字串表示數字的進位制:
var iNum1 = parseInt("10", 2); //返回 2
var iNum2 = parseInt("10", 8); //返回 8
var iNum3 = parseInt("10", 10); //返回 10
強制型別轉換
強制型別轉換在C++中有兩種方式:用括號將型別宣告在變數之前;或者呼叫建構函式。 在JavaScript中沒有型別關鍵字(只有一個var
來宣告變數),因而只能呼叫建構函式:
Boolean(0) // => false - 零
Boolean(new object()) // => true - 物件
Number(undefined) // => NaN
Number(null) // => 0
String(null) // => "null"
隱式型別轉換
隱式型別轉換是最為隱蔽的地方,不加註意的話很容易在這一點上出錯,對這一點的掌握也體現了JavaScript程式設計師經驗。 JavaScript會自動轉換表示式中物件的型別以完成表示式求值。
四則運算
加法運算子+
是雙目運算子,只要其中一個是String
型別,表示式的值便是一個String
。
對於其他的四則運算,只有其中一個是Number
型別,表示式的值便是一個Number
。
對於非法字元的情況通常會返回NaN
:
'1' * 'a' // => NaN,這是因為parseInt(a)值為NaN,1 * NaN 還是 NaN
判斷語句
判斷語句中的判斷條件需要是Boolean
型別,所以條件表示式會被隱式轉換為Boolean
。
其轉換規則同Boolean
的建構函式。比如:
var obj = {};
if(obj){
while(obj);
}
Native程式碼呼叫
JavaScript宿主環境都會提供大量的物件,它們往往不少通過JavaScript來實現的。 JavaScript給這些函式傳入的引數也會進行隱式轉換。例如BOM提供的alert
方法接受String
型別的引數:
alert({a: 1}); // => [object Object]