См. спецификацию : что он делает является :
Пусть r будет результатом выполнения абстрактного реляционного сравнения lval
, которое делает , которое пытается привести каждую сторону к первому примитиву:
а. Пусть px будет? ToPrimitive (x, номер подсказки).
b. Позволяет ли py быть? ToPrimitive (y, номер подсказки).
undefined
уже примитив - ничего не выбрасывает. Затем он делает:
Пусть nx будет? ToNumeric (px).
Пусть будет ny? ToNumeric (py).
Приведение undefined
к числу также не выбрасывает, но возвращает NaN
:
console.log(Number(undefined));
Итак, мы получаем
Если Type (nx) совпадает с Type (ny), вернуть Type (nx) ::lessThan (nx, ny).
, где nx
равно NaN
и ny
равно 0. lessThan
возвращает undefined
, когда nx
равно NaN
, описано здесь :
- Если x равен NaN, вернуть неопределенное значение.
А затем вернуться к шагу после 5.
в самом начале ответа:
Если r не определено, вернуть false. В противном случае верните r.
Результат равен undefined
, поэтому возвращается false
(без выдачи ошибки).
Таким образом, это должно быть
a.b.valueOf() > 0
Только объект будет вызывать valueOf
в процессе оценки <
(в a. Let px be ? ToPrimitive(x, hint Number).
выше). undefined
не является объектом - это уже примитив, поэтому на этом шаге не происходит никакого дополнительного преобразования.
Я определенно хотел, чтобы вместо этого была выдана ошибка.
Можно ли обработатьэто без явной проверки операндов?
Не совсем, но это совсем не сложно, просто убедитесь, что a.b
- это сначала число, если вы не уверены. if (typeof a.b === 'number')
. В этом нет ничего плохого.