Почему это происходит? Это из-за этого, где он возвращает строку вместо фактического undefined?
Ответ 1
Когда вы выполняете x.undefined, вы устанавливаете свойство x, называемое 'undefined'. Тот факт, что он имеет имя с undefined (a зарезервированное слово с переменной writable:false), является совпадением.
Позже, когда вы это сделаете, console.log(x[y]), вы ищете y в x. Ключами объектов являются строки, поэтому y преобразуется в строку. Когда undefined преобразуется в строку, он становится 'undefined'. Поэтому возвращается 'Hello World!'.
Ответ 2
Когда доступ к свойствам осуществляется с помощью нотации ., имя свойства не оценивается как выражение, это буквальная строка.
x.undefined
эквивалентно:
x['undefined']
Чтобы установить свойство с ключом undefined, вам нужно будет написать:
x[undefined] = "Bye, cruel world";
Интересно, что Chrome позволяет мне это делать.
Ответ 3
Вы определяете свойство "undefined" для x, но вы не переопределяете свойство "undefined" глобального объекта