Подтвердить что ты не робот

Почему работает [[]] [0] ++, но [] ++ генерирует исключение во время выполнения?

Почему первая строка работает, а вторая строка выбрасывает run-time exception?

Первая строка:

[[]][0]++; //this line works fine

Вторая строка:

[]++; //this lines throws exception
4b9b3361

Ответ 1

[[]][0]++

эквивалентно

var tmp = [[]];
tmp[0] = tmp[0]+1;

tmp[0] - пустой массив, который добавляется к числу 0, который увеличивается до 1.

Это работает только потому, что <array>[<index>]++ выглядит действительным. Требуется манипуляция типа, но он попадает туда.

Но []++ недействителен. Нет никакого способа сделать это имеющим смысл.

[] = []+1;

Левая часть здесь действительно недействительна. Вы не можете назначить пустой массив.

Ответ 2

Оператор ++ (или действительно любой постфиксный оператор) требует, чтобы операнд был "ссылкой", то есть значением, которому можно назначить. [] является литералом, поэтому вы не можете его назначить. [[]][0] - действительная ссылка на элемент временного массива.

0++; // not valid, `0` is a literal.
var a = [];
a++; // ok, `a` is assignable

Ответ 3

Это редкий случай, когда Javascript делает что-то, что действительно имеет смысл. Рассмотрим

x[3]++; // Valid
3++;    // Not valid

Если это имеет смысл для вас, то что удивительно в

[[]][0]++; // valid
[]++;      // not valid

<array>[index] - это "место", которое вы можете назначить или увеличить. Все это. Тот факт, что вы можете увеличивать a[<expr>], не означает, что вы можете увеличивать <expr>.

Абсурдная часть состоит в том, что вы можете использовать [] как индекс, который имеет смысл преобразовать массив в пустую строку "", а затем в число 0, но это известная проблема абсурдные неявные преобразования Javascript. Эти неявные правила преобразования - это большая бородавка Javascript и, например, подразумевают, что 1 == [1] или оба []==false и (![])==false.

Javascript - чистая бессмыслица во многих местах... но на самом деле не здесь.