2014-12-24 4 views
4

Github source codeПочему существует цикл while в методе setballbone?

Ниже приведен фрагмент метода набора Backbone в:

set: function(key, val, options) { 
    var attr, attrs, unset, changes, silent, changing, prev, current; 

    ... 

    options || (options = {}); 

    ... 

    // Trigger all relevant attribute changes. 
    if (!silent) { 
    if (changes.length) this._pending = options; 
    for (var i = 0, length = changes.length; i < length; i++) { 
     this.trigger('change:' + changes[i], this, current[changes[i]], options); 
    } 
    } 

    // You might be wondering why there's a `while` loop here. Changes can 
    // be recursively nested within `"change"` events. 
    if (changing) return this; 
    if (!silent) { 
    while (this._pending) { 
     options = this._pending; 
     this._pending = false; 
     this.trigger('change', this, options); 
    } 
    } 
    this._pending = false; 
    this._changing = false; 
    return this; 
} 

Хотя комментарий сделал упомянуть while петлю, я задаюсь вопросом о том, я не понимаю, как это работает в то время как петля с локальной переменной changing всегда будет true за один раунд set.

Может ли кто-нибудь объяснить мне, почему есть время и когда оно вступит в силу?

Заранее благодарен!

+0

Интересный вопрос. Не знаю ответа, мне придется проверить, что нужно знать. Но обратите внимание, что если 'change' истинно, то он выходит до цикла while. Если вы посмотрите немного раньше, изменение будет всегда ложным в первом событии изменения. Теперь, если событие изменения в цикле while запускает другое событие изменения, последующие изменения выходят до цикла while. Не знаю, почему. Ха-ха. – Gohn67

+1

Что произойдет, если прослушиватель событий ''change'' вызывает' set'? –

+0

@muistooshort - это то, что ваш комментарий Комментарий 'Изменения могут // быть рекурсивно вложенным в' 'change '' events' означает? Что кто-то звонит на событие 'change'? – seebiscuit

ответ

1

В комментарии говорится: «Изменения могут быть рекурсивно вложены в "change" событий».

Невозможно обновить или переустановить определенные свойства на вашей модели, когда происходит событие "change", а также сделать другой звонок set. Свойство _pending находится здесь, чтобы убедиться, что все свойства, обновленные на "change", даже изменены.

Похоже, что они использовали, чтобы проверить, есть ли дополнительные изменения, и если есть огонь, используемый для стрельбы just 1 change event. Проблема заключается в том, что если есть слушатель события изменения, который обновляет несколько объектов, не все функции set будут вызываться. См. this unit test для конкретного примера. Таким образом, петля while заботится о краевом корпусе 1 прослушивателя, вызывающего set несколько раз, а не нескольких слушателей, каждый вызов set один раз. Как этот в тесте связаны выше:

model.on('change:a', function() { 
    model.set({b: true}); 
    model.set({b: true}); 
}); 

Если вы смущены о том, почему они меняют this._pending к параметрам, проверить this issue & the associated pull request

+0

спасибо за ваш добрый ответ, однако я изменил 'while' в методе setballbone на' if', он все равно дает тот же результат. – jasonslyvia

+0

Вы правы, это не имело бы значения, потому что каждый новый вызов установить снова изменится, только если он в настоящее время не ожидается. Если будет выполнена одна и та же проверка. –

+0

, поэтому нет смысла использовать 'while' здесь вместо' if'? – jasonslyvia

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