当将简单比较作为watchExpression传递时,为什么此$watch触发两次?

$scope.foo = 0;  // simple counter

$scope.$watch('foo > 4', function() {
  console.log("foo is greater than 4: ", $scope.foo);
});

当页面加载时,当foo0时,侦听器将触发,然后当foo的值大于4时,触发一次(仅一次)。

为什么页面加载时会触发监听器?当foo大于4时,为什么它不继续触发?

我设置了一个简单的plunkr以显示正在发生的事情:http://plnkr.co/edit/ghYRl9?p=preview

最佳答案

重新阅读Angular $watch docs几次后,我想我了解发生了什么。



Angular在每个foo > 4循环中跟踪watchExpression digest()的值。因为在foo大于4之前,此方法评估为false,所以监听器不会触发。同样,在foo大于4之后,Angular正在比较的值都为true。它唯一检测到更改的时间是评估表达式越过时。

有两个值分别传递给$watch侦听器函数,新值和旧值。记录这些值表明正在对watchExpression进行评估,而Angular正在寻找这些值的更改。

$scope.$watch('foo > 4', function(newVal, oldVal) {
  console.log("foo is greater than 4: ", $scope.foo, oldVal, newVal);
});

// foo is greater than 4:  5 true false

还记录了在页面加载时调用侦听器的原因:



我用第二个$watch更新了plunkr,它在内部评估foo的值:

$scope.$watch('foo', function(newVal, oldVal) {
  if ($scope.foo > 4) {
  console.log("foo is greater than 4: ", $scope.foo, newVal, oldVal);
  }
});

// foo is greater than 4:  5 5 4
// foo is greater than 4:  6 6 5
// foo is greater than 4:  7 7 6

关于javascript - $ watch中的 Angular 表达式触发两次,我们在Stack Overflow上找到一个类似的问题:https://stackoverflow.com/questions/20942930/

10-12 13:01