Идея данной статьи пришла внезапно, после того как наткнулся на этот комикс, пришлось идти спрашивать пояснения шутки у людей сведущих в JavaScript и в процессе общения появился следующий материал:
В JS слабая динамическая типизация, нас интересует «слабая», это значит, что данные разных типов при совместных операциях преобразуются неявно, на лету. Так, если сложить 1 и 1 (числа), то ожидаемый результат 2. А если сложить строку «змее» и строку «ед», то получится «змееед». Пока всё ок. Но если смешать типы и сложить «змее» и число 1 получится: «змее1» так как в сложении участвует строка, число 1 неявно преобразуется в строку и складывается уже как строка. Таким образом, при сложении В яваскрипте «сильнее» строки. То есть ‘1’ + 1 будет строка ‘11’. И 1 + ‘1’ будет строка ‘11’
Что произойдёт при вычитании? При вычитании «сильнее» становятся числа (потому, что в яваскрипте вычитание строк не имеет смысла), то есть если в вычитании участвуют строка и число, интерпретатор попытается преобразовать все в числа. ‘1’ - 1 = 0. А если не получится, то «змее» - 1 = NaN (NaN - это специальное значение Not a Number)
Что получится в примере из комикса?
1 + ‘1’ - 1
Преобразования прйдут последовательно: после первого сложения строки и числа мы получим строку ‘11’, а после вычитания числа 1 число 10.
А, например, это: ‘1’ - 1 + ‘1’
Даст нам строку ‘01’.
Вот эта зависимость результата от порядка действий и невозможность его предсказать «с первого взгляда» и является предметом шутки.
Что же получится в итоге? 1? ‘10’ или NaN? Стресс! 💡 💡💡💡💡
Хотя опытные разработчики в курсе такого поведения (оно документировано и хорошо известно) и скорее всего не будет их стрессовать.
https://jsfiddle.net/Basille/8gpk0vht/
__________________________________________________________________________________________
<p id="sum"></p>
<p id="diff"></p>
<p id="snake"></p>
__________________________________________________________________________________________
let sum=1+'1'-1;
let diff='1'-1+'1';
let snake='змее'-1+'1'
document.getElementById("sum").textContent="1 + '1' - 1 = "+sum
document.getElementById("diff").textContent="1 - '1' + 1 = "+diff
document.getElementById("snake").textContent="змее - '1' + 1 = "+snake