Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Make toPrimitive conversion depend on the context [duplicate]

I want an object to return one value in a numeric context and a completely different one in a string context. The following doesn't work.

foo = {
    toString: function() { return "string" },
    valueOf:  function() { return 123 }
}

console.log(foo * 2)       // got 246, fine
console.log("hi " + foo)   // got "hi 123", want "hi string"
like image 764
georg Avatar asked Jun 14 '13 12:06

georg


1 Answers

The addition operator will convert both operands to primitives using the internal abstract operation ToPrimitive, and then, if one operand is a string, it will use the internal abstract operation ToString to convert both to strings (note: this is different from the toString method on userland objects.)

The upshot is, that with addition of Symbol.toPrimitive to the language, you can now achieve your goal:

const foo = {
  [Symbol.toPrimitive](hint) {
    switch (hint) {
      case "string":
      case "default":
        return "string"
      case "number":
        return 123
      default:
        throw "invalid hint"
    }
  }
}

console.log(foo * 2) // 246
console.log("hi " + foo) // "hi string"
like image 115
Alnitak Avatar answered Sep 22 '22 09:09

Alnitak