詳解JavaScript對象轉原始值

Object.prototype.valueOf()

對象的valueOf旨在返回對象的原始值,會在需要將對象轉換成原始值的地方自動執行。詳細點這裡。

Object.prototype.toString()

toString()方法會返回表示該對象的字符串,會在對象預期要被轉換成字符串的地方自動執行。對象默認的toString()方法會返回[object type],這個type就是對象構造函數的名稱。詳細點這裡。

Symbol.toPrimitive

Symbol.toPrimitive(hint)方法作用同valueOf()一樣,但是優先級要高於valueOf();而且該方法還會接受一個參數hint,這個參數用來表示期望轉換的原始值的具體類型,有以下幾種:

  • number:數字類型
  • string:字符串類型
  • default:默認
let obj = {
  [Symbol.toPrimitive](hint) {
    switch (hint) {
      case 'number':
        return 123;
      case 'string':
        return 'str';
      case 'default':
        return 'default';
      default:
        throw new Error();
     }
   }
};
2 * obj // 246
3 + obj // '3default'
obj == 'default' // true
String(obj) // 'str'

對象轉換原始值

以上三種方法都是在對象被預期轉換成某種原始值時觸發。

1. 預期被轉換成字符串類型

對應的hint類型為string

進行輸出的地方,如alert()

String(obj)

let a = {
  toString () {
    return '2'
  }
}
console.log(String(a)) // 2

字符串連接(+)操作

let a = {
  toString () {
    return '2'
  }
}
console.log(a + 'vv')

模板字符串

let a = {
  [Symbol.toPrimitive] (hint) {
    console.log(hint) // string
    return 2
  }
}
console.log(`你是老${a}?`) // 你是老2?

2. 預期被轉換成數字類型

對應的hint類型為numbe

除法:

let a = {
  valueOf () {
    return 2
  }
}
console.log(2 / a, a / 2) // 1  1

Number(obj):

let a = {
  [Symbol.toPrimitive] (hint) {
    console.log(hint) // number
    return 2
  }
}
console.log(Number(a)) // 2

正負號(註意不是加減運算):

let a = {
  [Symbol.toPrimitive] (hint) {
    console.log(hint) // number
    return 2
  }
}
console.log(+a) // 2
console.log(-a) // -2

3. 預期被轉換成默認類型(其他)

對應的hint類型為default

數字加法(即與對象相加的一方為數字類型):

let a = {
  [Symbol.toPrimitive] (hint) {
    console.log(hint) // default
    return 2
  }
}
console.log(1 + a) // 3

這一點有點意外,原以為像這種情況預期轉換的類型應該是數字類型,但事實上卻是default;

佈爾運算:所有對象都被轉換成true;

let a = {
  [Symbol.toPrimitive] (hint) {
    console.log(hint) // 沒有觸發
    return false
  }
}
console.log(Boolean(a), a && 123) // true 123

佈爾運算包括==

三種方法觸發的順序

首先判斷對象是否有Symbol.toPrimitive(hint)方法,若有則執行該方法,沒有則執行下面的步驟;

如果預期被轉換成字符串類型時,則優先執行toString()方法;

如果預期被轉換成默認類型或者數字類型時,則優先執行valueOf()方法:

:若沒有valueOf()方法,但是定義瞭toString()方法,則會執行toString()方法;

總結

本篇文章就到這裡瞭,希望能夠給你帶來幫助,也希望您能夠多多關註WalkonNet的更多內容!

推薦閱讀: