数字比较运算符对 BigInt 和 Number 的强制转换

BigInt and Number coercion by numeric comparison operators

BigInt 和 Number 之间的数值比较是将一个参数强制转换为 BigInt,还是将一个参数强制转换为 Number?

比如下面,是3n被强制转换为3,还是1被强制转换为1n

console.log(3n > 1) // true

两个操作数似乎都是 converted to a "mathematical value" in 4.k of the IsLessThan abstract operation; a process that is designated ℝ in the specification

不过我不知道这是什么意思。

我注意到:

console.log(19_999_999_999_999_998 > 19_999_999_999_999_999n) // true

也许 19,999,999,999,999,998 的“数学值”ℝ 是值 20,000,000,000,000,000 的描述符,这是最接近的 IEEE754 表示形式?

我仍然不明白是否可以说发生强制转换,因为 Number 可以有小数部分,而 BigInt 不能。

Because coercing between Number values and BigInt values can lead to loss of precision, the following are recommended:

Only use a BigInt value when values greater than 2^53 are reasonably expected. Don't coerce between BigInt values and Number values.

BigInt 转换为 Number(这会导致精度损失)。

https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/BigInt

更新:

对于3n > 1

Bytecode length: 11
Parameter count 6
Register count 2
Frame size 16
OSR nesting level: 0
Bytecode Age: 0
   16 S> 0x28001122e @    0 : 13 00             LdaConstant [0]
         0x280011230 @    2 : c2                Star1 
         0x280011231 @    3 : 0d 01             LdaSmi [1]
   20 E> 0x280011233 @    5 : 6d f9 00          TestGreaterThan r1, [0]
         0x280011236 @    8 : c3                Star0 
         0x280011237 @    9 : 0e                LdaUndefined 
   24 S> 0x280011238 @   10 : a8                Return 
Constant pool (size = 1)
0x2800111c9: [FixedArray] in OldSpace
 - map: 0x0a554d7412c1 <Map>
 - length: 1
           0: 0x0002800111e1 <BigInt 3>
Handler Table (size = 0)
Source Position Table (size = 8)
0x000280011241 <ByteArray[8]>

对于TestGreaterThan,看起来比较的是两个固定数组(BigInt & Int)

Will numeric comparison between a BigInt and a Number coerce one argument to BigInt, or coerce one argument to Number?

都没有。正如您在规范中阅读的那样,比较了它们的数学值。

考虑 2n < 2.4。如果两者都转换为 BigInt,您将得到一个异常(“无法将 non-integer 转换为 BigInt”)或者您将得到结果 false 因为2n不小于2n。但是不,我们得到结果 true 因为“ℝ(2n) < ℝ(2.4)”是“2 < 2.4”,这是真的。

考虑 9007199254740993n > 9007199254740992。如果两者都转换为数字值,您将得到结果 false,因为 9007199254740993 大于 Number.MAX_SAFE_INTEGER 并失去精度,成为不大于 [=] 的数字值 9007199254740992 20=]。但是不,我们得到结果 true 因为“ℝ(9007199254740993n) > ℝ(9007199254740992)”是“9007199254740993 > 9007199254740992”,这是真的。

Perhaps the "mathematical value", ℝ, is the closest possible IEEE754 representation?

不,那是 Number value for x, also denoted as (x), which converts from a mathematical value (the real numbers) or extended mathematical value (the real numbers plus two infinities) to a concrete (IEEE 754 double-precision floating point) Number。数学值是抽象的,有很多实数既不能准确表示为 BigInt 或 Number。