Welcome to OGeek Q&A Community for programmer and developer-Open, Learning and Share
Welcome To Ask or Share your Answers For Others

Categories

0 votes
804 views
in Technique[技术] by (71.8m points)

language lawyer - Are JavaScript template literals guaranteed to call toString()?

const num = 42
const str = `My number is ${num}`

In this code what guarantee do I have about the conversion of num to a string ?

Is it guaranteed to just call its toString() method or could the conversion be done in another way ?

See Question&Answers more detail:os

与恶龙缠斗过久,自身亦成为恶龙;凝视深渊过久,深渊将回以凝视…
Welcome To Ask or Share your Answers For Others

1 Reply

0 votes
by (71.8m points)

Untagged templates use the ECMAScript ToString() abstract operation. The logic of template literal evaluation is spread over several sections which makes it difficult to follow, so I'll just post a link to it: https://tc39.es/ecma262/#sec-template-literals-runtime-semantics-evaluation

ToString(argument) uses a table instead of algorithmic steps, so I'll write out some pseudocode here:

switch (Type(argument)) {
  case 'Undefined':
    return 'undefined';
  case 'Null':
    return 'null';
  case 'Boolean':
    return argument ? 'true' : 'false';
  case 'Number':
    return Number::toString(argument);
  case 'String':
    return argument;
  case 'Symbol':
    throw new TypeError();
  case 'BigInt':
    return BigInt::toString(arugment);
  case 'Object':
    return ToString(ToPrimitive(argument, 'string'));
}

As you can see, no js execution happens at all for primitive values, the engine internally creates a string representation. For objects, we go into the ToPrimitive() algorithm.

ToPrimitive(input, PreferredType) will try to get the Symbol.toPrimitive method from input, and if it's present, call it with the given PreferredType hint. If input does not have a Symbol.toPrimitive property, it falls back to OrdinaryToPrimitive.

OrdinrayToPrimitive(O, hint) will try to call the toString and valueOf methods. If hint is 'string', it try to call toString method first, otherwise it will try to call the valueOf method first. If either of those methods are present and they don't return an object, their return value will be used. If neither are present or they both return objects, a TypeError will be thrown.

So to answer your original question, converting 42 will not call any other methods. The engine will internally create a string representation ('42'), and use that.


与恶龙缠斗过久,自身亦成为恶龙;凝视深渊过久,深渊将回以凝视…
OGeek|极客中国-欢迎来到极客的世界,一个免费开放的程序员编程交流平台!开放,进步,分享!让技术改变生活,让极客改变未来! Welcome to OGeek Q&A Community for programmer and developer-Open, Learning and Share
Click Here to Ask a Question

...