аргументы функции - PullRequest
       16

аргументы функции

9 голосов
/ 19 марта 2009
function Foo(f) {
   var f = f;    
}

Здесь внутри функции переменная f является локальной для Foo (она имеет область действия функции), но почему переменная f в списке аргументов не конфликтует? Может быть, потому что он связан внутри Foo.arguments объекта?

В других языках мы не можем объявить переменную аргумента с тем же именем, что и локальная переменная.

Как разрешается эта двусмысленность имени? Или, как вы ссылаетесь на каждую из двух отдельных f переменных позже в методе?

Ответы [ 5 ]

12 голосов
/ 19 марта 2009

JavaScript делает несколько вещей, которые явно не интуитивны - то, что вас интересует, называется «подъем» - JS перемещает объявления var в верхнюю часть функции, где они служат единственной цели резервирования этой переменной имя в качестве локальной переменной в области видимости функции. Иногда это приводит к большому количеству странностей . Если имя переменной уже зарезервировано как локальная переменная (например, это аргумент), объявление var полностью удаляется.

Другая неинтуитивная часть JS - это то, как он работает с переменными аргумента и объектом arguments (которые, как показал Бегемот, немного особенные). Однако это не обязательно то, что вас интересует - для вашего примера важно то, что аргументы также объявляют это имя переменной как локальное для функции.

Результатом всего этого является то, что, когда у вас есть var f, а также имя аргумента f, `var f 'отбрасывается, и ваш пример эквивалентен:

function Foo(f) {
   f = f;
}

Вы можете увидеть это на примере Бегемота, потому что:

function foo(f) {
    console.log(f); // --> 11
    console.log(arguments); // --> array [11]
    var f = 10;
    console.log(f); // --> 10
    console.log(arguments); // --> [10] (!!!)
}

Эквивалентно:

function foo(f) {
    var f;
    console.log(f); // --> 11
    console.log(arguments); // --> array [11]
    f = 10;
    console.log(f); // --> 10
    console.log(arguments); // --> [10] (!!!)
}

Эквивалентно:

function foo(f) {
    console.log(f); // --> 11
    console.log(arguments); // --> array [11]
    f = 10;
    console.log(f); // --> 10
    console.log(arguments); // --> [10] (!!!)
}

Для получения более подробной информации прочитайте раздел 10.1.3 - Переменная Instantiation (нижняя часть стр.37) в ECMA-262 , спецификация JS.

6 голосов
/ 19 марта 2009

Нет способа решить эту проблему, кроме переименования одного из них или сохранения значения в другой переменной.

function foo(f) {
    console.log(f); // --> 11
    console.log(arguments); // --> array [11]
    var f=10;
    console.log(f); // --> 10
    console.log(arguments); //even this is now array [10]
}
foo(11);
2 голосов
/ 19 марта 2009

Как только вы объявляете новую переменную с тем же именем, что и у старой, она переопределяет ее, и вы не можете ссылаться на обе одновременно.

Вам следует либо изменить параметр, либо имя переменной.

1 голос
/ 19 марта 2009

здесь внутри функции переменная f является локальной для Foo (она имеет область действия функции), но переменная f в списке аргументов, которая названа таким же образом, почему она не находится в конфликте, может быть, потому что она связана внутри Объект Foo.arguments?

Нет, он не связан с аргументами: аргументы - это только массив значений позиционных аргументов, из него нельзя получить «arguments.f».

Аргументы, переданные в функцию по имени, становятся локальными переменными. «Var f» в функции с аргументом «f» неявный.

Когда вы объявляете переменную, которая уже является локальной, ничего не происходит. Ваш код идентичен:

function Foo(f)
{
    f = f;
}

В других языках мы не можем объявить переменную аргумента с тем же именем, что и локальная переменная.

В JavaScript, если в блоке области видимости используется «var x», любое использование «x» в этом блоке является локальным. Вы можете с радостью снова и снова объявлять «var» для одной и той же переменной в одной и той же области видимости, но это ничего не делает.

0 голосов
/ 19 марта 2009

В Firefox я заметил, что объявление новой переменной не принесло никакого вреда, это почти так, как если бы для этого не было положения

  <script type="text/javascript">

  function saymessage(f) {
    alert(f);
    var f = f;
    alert(f);
    alert(this.f);
  }
  </script>
</head>

<body >

  <!-- Insert Body Here -->
<button  id='link' textToShow="Hidden message text" onclick="saymessage('Hello World')">Click me </button>

</body>

Я получил «Hello World» в 1-м и 2-м оповещениях и «undefined» в третьем

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...