2008-10-28 4 views
3

Влияние размещения функции влияет на производительность закрытий в пределах области видимости? Если да, то где оптимальное место для размещения этих функций? Если нет, подразумевается ли ассоциация закрытием достаточно оснований для логического размещения функции в другом месте?Закрытие и назначение функций javascript

Например, если Foo не зависит от значения localState, делает тот факт, что localState доступен из Foo иметь последствия как для обув «ы времени выполнения, использование памяти, и т.д.?

(function(){ 
    var localState; 

    function foo(){ 
     // code 
    } 

    function bar(){ 
     // code 
     return localState; 
    } 
})(); 

Другими словами, будет ли это лучший выбор, и если да, то почему?

(function(){ 
    function foo(){ 
     // code 
    } 

    var localState; 

    function bar(){ 
     // code 
     return localState; 
    } 
})(); 

Darius Bacon предложил below, что два образца выше, являются идентичными, так как localState могут быть доступны в любом месте внутри блока. Однако пример ниже, где foo определяется вне блока, может быть другим случаем. Как вы думаете?

function foo(){ 
    // code 
} 

(function(){ 

    var localState; 

    function bar(){ 
     // code 
     foo(); 
     return localState; 
    } 
})(); 

ответ

3

Каждая функция в Javascript является закрытием. Время выполнения для разрешения значения переменной возникает только в том случае, если функция ссылается на эту функцию.Например, в этом примере функция у фиксирует значение х, даже если х не ссылается непосредственно у:

var x = 3; 
function y() eval("x"); 
y(); 
3 
1

Объем объявления var или функции - это весь блок, в котором он находится, независимо от того, где находится в блоке объявление; поэтому было бы удивительно, если бы это повлияло на эффективность.

То есть, не имеет значения, является ли «функция foo()» до или после «var localState» внутри этого блока. Это may имеет значение «функция foo()» в этом блоке или в приложении (если его можно поднять до более высокой области видимости, поскольку она не использует любые локальные переменные); это зависит от деталей вашего Javascript-компилятора.

2

Я не думаю, что накладные расходы были бы слишком высокими, так как java-скрипт не использует понятие стека функций. Он поддерживает лексику. Одно и то же состояние осуществляется через вызовы закрытия. С другой стороны, в вашем примере вы, похоже, не выполняете никаких утверждений!

+0

Вы правы! Я попытался предположить некоторое исполнение с комментариями «// code», но, видимо, было не очень понятно. Спасибо за Ваш ответ. – brad 2008-10-28 17:24:07

5

Оба эти фрагмента эквивалентны, поскольку оба они определены в (той же) среде анонимной функции, которую вы создаете. Я думаю, вы сможете получить доступ к localState от foo в любом случае.

Это говорит о том, что если у вас есть абсурдные количества переменных в среде, которую вы создаете, тогда может повлиять время выполнения foo, так как переменные запросы, вероятно, затянутся дольше. Если есть много переменных, которые вы больше не используете в функции, которую вы определяете foo, а foo тоже не нужны, то foo не заставит их не собирать мусор, так что это также может быть проблемой.

+0

Фактически, чтобы убедиться, что JS действительно закрывает неиспользуемые переменные, попробуйте следующее: (function() {var a = 1; return function (x) {eval (x)}})() ("alert (a) ") Очевидно, что внутренняя функция не ссылается на` a`, но она доступна. – ephemient 2008-10-28 20:12:57

+0

В отличие от Perl, sub {my $ a = 1; sub {eval $ _ [0]}} ->() ('print $ a'), ничего не печатает, но sub {my $ a = 1 ; sub {$ a; eval $ _ [0]}} ->() ('$ a'): Perl заботится о том, ссылается ли переменная, чтобы определить, закрыта ли она. – ephemient 2008-10-28 20:18:22

5

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

0

В ваших примерах разница не имеет большого значения. Даже если foo находится в глобальной области, у вас не будет проблемы.

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

Для лучшей идеей, попробуйте следующие два примера:

CheckOne(); 
function CheckOne() { 
    alert('check...check one.'); 
} 

CheckTwo(); 
var CheckTwo = function() { 
    alert('check...check two.'); 
}; 

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

Cheers.

 Смежные вопросы

  • Нет связанных вопросов^_^