Skip to content

JS Symbol.toPrimitive 详解

Published: at 05:19 PMSuggest Changes

问题

群友大佐出了一道题

add[1] + 1 // 2
add[1][2][3] + 4 // 10
add[10][-5][3][100] * 2 // 216

解答

他在 stackoverflow 有过提问

https://stackoverflow.com/questions/71688697/how-do-i-achieve-this-curry-function-add-with-square-bracket-notation

let add = new Proxy(
  {
    [Symbol.toPrimitive]() {
      return this.value;
    },
    value: 0
  },
  {
    get(target, key, receiver) {
      if(key === Symbol.toPrimitive) {
        return target[key];
      } else if(key === 'value') {
        const sum = target[key];
        target[key] = 0;
        return sum;
      } else if (!isNaN(key)) {
        target.value += +key;
      }
      return add;
    },
  }
);

console.log(+add[1]);
console.log(+add[1][2][3]);
console.log(+add[10][-5][3][100]);

从上面的代码可以看出,add 是一个 Proxy 对象,它的 value 属性是一个 Symbol.toPrimitive 方法,当 add 被转换为原始值时,会调用 Symbol.toPrimitive 方法,返回 value 属性的值。

而且里面的 + 也比较关键,不然无法在 runtimte 里面调用

知识点

Symbol.toPrimitive

Symbol.toPrimitive 是一个内置的 Symbol 值,它是一个方法,当一个对象转换为原始值时,会调用这个方法,返回原始值。

const obj = {
  [Symbol.toPrimitive](hint) {
    console.log(hint);
    return 1;
  }
};

console.log(+obj); // "number"

console.log(`${obj}`); // "string"

console.log(obj + 1); // "default"

具体可以看一下

https://zh.javascript.info/object-toprimitive#symboltoprimitive


Previous Post
CSS 碰撞变色小球
Next Post
JavaScript 毫秒级定时器