JavaScript有哪些資料型別?

有只橘猫發表於2024-09-26

JavaScript共有八種資料型別,分別是 Undefined、Null、Boolean、Number、String、Object、Symbol、BigInt。

Symbol 和 BigInt

其中Symbol 和 BigInt 是 ES6+(ECMAScript 2015+)中新增的資料型別:

  • Symbol 可以理解為一個獨特的識別符號。想象一下,你有一把獨一無二的鑰匙,這把鑰匙就是 Symbol。它的主要用途是避免在使用物件屬性時發生意外的名字衝突。比如,如果你和別人合作開發一個大型專案,你們都想給一個物件新增一個叫"id"的屬性,使用 Symbol 可以確保你們的"id"不會互相覆蓋。
  • BigInt 是專門用來處理特別大的整數的。普通的 Number 型別在JavaScript中有一個最大安全整數(9007199254740991),超過這個數字可能會出現計算錯誤。而 BigInt 可以安全地表示和計算任意大的整數,就像是給了數字一個無限的跑道。比如,當你需要精確計算天文數字或者處理非常大的金融資料時,BigInt 就非常有用。

這兩種資料型別的加入,使得 JavaScript 能夠更好地處理獨特標識和超大整數,增強了語言的功能性和適用範圍。

簡單型別和複雜型別

JavaScript 的資料型別可以分為兩大類:簡單型別和複雜型別。

  1. 簡單型別(也叫原始型別)

    • 這些型別就像是一個個小盒子,每個盒子裡直接裝著一個值。
    • 包括:Undefined、Null、Boolean、Number、String、Symbol 和 BigInt。
    • 它們儲存在計算機的"棧"記憶體中,就像一摞盤子,取用方便快捷。
  2. 複雜型別(也叫引用型別)

    • 這些型別更像是大箱子,裡面可以裝很多東西。
    • 主要是 Object 型別,包括普通物件、陣列和函式。
    • 它們儲存在"堆"記憶體中,就像一個大倉庫,可以存放更多、更復雜的資料。

簡單來說,簡單型別就是單純的資料,複雜型別則可以包含更多資訊和功能。

兩種型別的區別在於儲存位置的不同:

  • 棧記憶體:原始資料型別就像是小紙條,上面寫著簡單的資訊(如數字或文字)。這些小紙條直接放在一個叫"棧"的抽屜裡。這個抽屜很小,但是拿東西特別快,所以經常用到的小紙條就放在這裡。
  • 堆記憶體:引用資料型別則像是大箱子,裡面可能裝著很多東西(如各種衣物)。這些大箱子放在一個叫"堆"的大倉庫裡。因為箱子太大了,不能直接放在小抽屜裡,所以我們在小抽屜裡放了一張寫有箱子位置的便利貼。當我們需要箱子裡的東西時,先在抽屜裡找到便利貼,然後按照便利貼上的位置資訊去倉庫裡找到對應的箱子。

資料型別檢測

  • typeof: 7種基礎資料型別中除了 null 返回的是 object,其他都能準確返回(包括 Symbol 返回 symbol,BigInt 返回 bigint),複雜資料型別中 Function 型別的資料返回 function,其他都返回 object;

console.log(typeof 42);           // 輸出: "number"
console.log(typeof "Hello");      // 輸出: "string"
console.log(typeof true);         // 輸出: "boolean"
console.log(typeof Symbol());     // 輸出: "symbol"
console.log(typeof 42n);          // 輸出: "bigint"
console.log(typeof null);         // 輸出: "object"
console.log(typeof {});           // 輸出: "object"
console.log(typeof []);           // 輸出: "object"
console.log(typeof function(){}); // 輸出: "function"
  • instanceof: 複雜資料型別如Array等都準確返回相應的boolean值,對於基本資料型別則是返回 false (只有是透過new運算子來進行初始化,然後透過instanceof來判斷是否是某個類的例項,才會返回true,比如"var k = new Number(11); console.log(k instanceof Number)",其返回true);

console.log([] instanceof Array);               // 輸出: true
console.log({} instanceof Object);              // 輸出: true
console.log(new Date() instanceof Date);        // 輸出: true
console.log(42 instanceof Number);              // 輸出: false
console.log(new Number(42) instanceof Number);  // 輸出: true
  • 使用constructor檢測:上面的instanceof對於直接宣告如:"var a = 1;" 不能進行判斷,我們可以透過使用constructor來實現判斷,如 "a.constructor==Number" (其返回true,不過對於"1.constructor==Number"這類直接用數值來訪問 constructor 的情況是會報錯的),但對於null則仍然無法判斷 ,而且會報錯,比如"var k = null; console.log(k.constructor==Object)";

console.log((42).constructor === Number);        // 輸出: true
console.log("Hello".constructor === String);     // 輸出: true
console.log([].constructor === Array);           // 輸出: true
console.log(({}).constructor === Object);        // 輸出: true
// console.log(null.constructor === Object);     // 這行會報錯
  • 使用Object.prototype.toString.call使用:這個方法可以獲取所有的型別(包括null型),不過其返回的是類似"object Array"的形式的字串。

console.log(Object.prototype.toString.call(42));           // 輸出: "[object Number]"
console.log(Object.prototype.toString.call("Hello"));      // 輸出: "[object String]"
console.log(Object.prototype.toString.call(true));         // 輸出: "[object Boolean]"
console.log(Object.prototype.toString.call(null));         // 輸出: "[object Null]"
console.log(Object.prototype.toString.call(undefined));    // 輸出: "[object Undefined]"
console.log(Object.prototype.toString.call([]));           // 輸出: "[object Array]"
console.log(Object.prototype.toString.call({}));           // 輸出: "[object Object]"
console.log(Object.prototype.toString.call(function(){})); // 輸出: "[object Function]"

注意事項

  1. null的型別檢測:

    • 使用typeof null會返回"object",這是 JavaScript 的一個歷史遺留 bug。
    • 要準確檢測null,可以使用嚴格相等:value === null
  2. 原始值包裝物件:

    • JavaScript 會自動為原始值建立包裝物件,這就是為什麼我們可以在原始值上呼叫方法。
    • 例如:"hello".toUpperCase()實際上 JavaScript 會臨時建立一個 String 物件。
  3. Symbol 的特殊性:

    • Symbol 值是唯一的,即使描述相同,兩個 Symbol 也不相等。
    • 例如:Symbol('foo') !== Symbol('foo')
  4. BigInt 的使用:

    • BigInt 數字後面要加n,例如:const bigInt = 1234567890123456789012345678901234567890n;
    • BigInt 不能與普通數字進行混合運算。
  5. 型別轉換:

    • JavaScript 中的型別轉換可能會導致意外結果,例如:

console.log([] + []); // 輸出空字串 ""
console.log([] + {}); // 輸出 "[object Object]"
console.log({} + []); // 輸出 0 (在某些環境下)

相關文章