Могу ли я нацелить несколько объектов с помощью одной операции, используя оператор `with` ECMAScript? - PullRequest
0 голосов
/ 03 мая 2011

Следующее не работает (хотя оно и не дает явной ошибки), но почему нет?

И ... Есть ли действительно нет возможности вокругэто, строго используя с утверждением ?Забудьте , используя for / foreach .

with (object1, object2) {
  attribute = value;
  method();
}

edit: Извините, что задаю 2 вопроса в 1. Я постараюсь прояснить ситуацию:

  1. Почему приведенный выше код не дает синтаксической ошибки, не работает, но принимается with?

  2. Если это возможно, как мы можем изменить несколькообъекты с одинаковым атрибутом, использующие with?

Надеюсь, следующий пример будет более понятным для того, чего я хотел достичь:

var object1 = { attribute: 3 };
var object2 = { attribute: 2, method: function() { alert('blah'); } };
var object3 = { method: function() {alert('bleh'); } };

var value = 4;

with (object1) 
with (object2) 
with (object3) 
{
  attribute = value;
  method();
}

alert(object1.attribute + object2.attribute);

// resulting alerts should be, in order: blah, bleh, 8

Ответы [ 2 ]

6 голосов
/ 03 мая 2011

Введение в многоцелевую область с with

Это то, что я первоначально думал, что вы были после, так как вы не указали, каковы ваши ожидаемые результаты. Просто сложите with операторов:

var object1 = { attribute: 3 };
var object2 = { method: function() { alert('blah'); } };

var value = 4;

with (object1) 
with (object2) 
{
  attribute = value;
  method();
}

alert(object1.attribute);

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

Стандартные заявления об отказе применяются в отношении снижения производительности и вероятности ошибок, вызванных использованием with. Обратите внимание, что ваш пример показывает доступ к свойству с префиксом . внутри блока, но это неверно - with изменяет область действия, временно помещая объект в начало цепочки разрешения, поэтому префикс не требуется (или не разрешен).


Ориентация на несколько объектов

Относительно вашего редактирования: оператор запятой позволяет вам написать что-то, что появляется для передачи нескольких выражений в with, но на самом деле только одно из них. Вы не сможете выполнить то, что хотите, без какой-либо реализации многоадресного делегата (та, которая включает в себя зацикливание); В JavaScript / ECMAScript нет встроенных средств изменения нескольких свойств / вызова нескольких методов с помощью одного присваивания / вызова.

Быстрая и грязная реализация:

function multicast()
{
  this.targets = Array.prototype.slice.call(arguments, 0);
}
multicast.prototype = {
  call: function(methodName)
  {
    var i;
    for (i=0; i<this.targets.length; ++i)
    {
      if ( this.targets[i][methodName] )
        this.targets[i][methodName].apply(this.targets[i],
          Array.prototype.slice.call(arguments, 1));
    }
  },
  set: function(propName, value)
  {
    var i;
    for (i=0; i<this.targets.length; ++i) 
      this.targets[i][propName] = value;
  }
};

Использование:

var object1 = { attribute: 3 };
var object2 = { attribute: 2, method: function() { alert('blah'); } };
var object3 = { method: function() {alert('bleh'); } };

var value = 4;

var delegate = new multicast(object1, object2, object3);
delegate.set('attribute', value);
delegate.call('method');

alert(object1.attribute + object2.attribute);
2 голосов
/ 03 мая 2011

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

var o1 = object1
,   o2 = object2
;
o1.attribute = value;
o2.method();
...