#javascript
#javascript
Вопрос:
Я использую JavaScript для написания некоторого кода и обнаружил неожиданное поведение.
Я использую вложенную функцию g
внутри f
. f
имеет параметр с именем m
. При использовании и объявлении переменной внутри g
с тем же именем происходит что-то странное:
var f = function(m) {
var g = function() {
alert(m);
var m = 0;
};
g();
};
f(1);
Результатом этого кода будет undefined
, вместо 1
того, что я ожидал.
Перемещение alert
инструкции ниже var
строки приведет к ответу 0
, который имеет смысл.
Я полагаю, это связано с тем, что JavaScript использует функции только в качестве замыкания имени, var m
будет присоединен к функции g
с объявлением, но m
еще не назначен во время alert
.
Но я не уверен в этом, потому что, если функция не вложена, ее поведение мне кажется приятным:
var g = function(m) {
alert(m);
var m = 0;
};
g(1);
привело бы к 1
.
Кто-нибудь может объяснить? Спасибо.
Комментарии:
1. Существует ли какой-либо другой код, который может повлиять на это? Поведение здесь не такое, как вы описываете: jsfiddle.net/QvcqU
2. @shanethehat: извините, я имел в виду
undefined
.3. Когда я запускаю ваш первый блок кода, я получаю undefined.
4. @herostwist: да, это
undefined
. Я отредактировал вопрос.5. Причина, по которой второй выдает 1, заключается в том, что у вас есть m в качестве формального параметра, затем передайте 1 функции, чтобы ей присваивалось значение при вызове функции. Позже m устанавливается в 0, когда обрабатывается присвоение m=0.
Ответ №1:
Javascript использует область видимости функции, что означает, что область видимости переменных не похожа на область видимости блока C, входящую и выходящую из области видимости в соответствии с {}
, а скорее объекты входят и выходят из области видимости в соответствии с началом и окончанием функций. Таким образом, каждая локальная переменная, которую вы определяете в функции, объявляется с начала выполнения этой функции и будет иметь тип undefined
до тех пор, пока вы не инициализируете ее в своей функции.
Таким образом, при g
выполнении, поскольку в какой-то момент будет создана локальная переменная m
, среда выполнения уже объявляет, что существует локальная m
(которая, очевидно, скрывает внешний m f
функции) с типом undefined
с начала g
выполнения
Смотрите https://developer.mozilla.org/en/JavaScript/Reference/Scope_Cheatsheet это объясняет, что при выполнении этого действия var varName
переменная поднимается в верхнюю часть области видимости функции. На этой странице много отличных примеров, вот одна цитата, которая подводит итог:
Каждое определение переменной на самом деле является объявлением переменной в верхней части ее области видимости и присвоением в месте, где находится определение.
Комментарии:
1. Хотя это объяснение звучит разумно, я не думаю, что оно отвечает на вопрос, а именно, почему параметры обрабатываются иначе, чем определения во внешней области видимости. Я предполагаю, что ответом вполне может быть: именно так оно и есть.