【问题标题】:Watch variable and change it观察变量并改变它
【发布时间】:2014-10-08 23:23:06
【问题描述】:

在 AngularJS 中,我有一个监视范围变量的指令。当变量包含某些数据时,我需要稍微更改该变量。问题是当我更改变量时,我的$watch 再次被触发。所以我最终陷入了一个连续的循环。

scope.$watch('someVar', function(newValue, oldValue) {
    console.log(newValue);
    scope.someVar = [Do something with someVar];
});

这会再次触发$watch,这是有道理的。但我确实需要一种方法来更改监视变量。有没有办法做到这一点?

【问题讨论】:

  • 使用另一个布尔值管理它

标签: angularjs watch


【解决方案1】:

这就是脏检查的工作原理。每次$scope 上的某些内容发生更改时,Angular 都会遍历范围内的所有内容,并且会一直这样做,直到没有更多更改为止。

如果你想做这样的事情,你必须确保你的$watch 函数是幂等的。您必须同时查看 newValueoldValue 并确定您是否已经在此 $digest 循环中将更改应用于变量。如何做到这一点取决于您对someVar 所做的更改。

一般来说,不幸的是,在监视函数中更改监视变量不是一个好主意。

【讨论】:

    【解决方案2】:

    是的,你可以像这样取消它

    var wathcer = scope.$watch('someVar', function(newValue, oldValue) {
        console.log(newValue);
        scope.someVar = [Do something with someVar];
    
    });
    wathcer(); // clear the watch
    

    【讨论】:

      【解决方案3】:

      函数内部使用 if 条件来避免继续循环

      scope.$watch('someVar', function(newValue, oldValue) {
         if(newValue!==oldValue) {
          console.log(newValue);
          scope.someVar = [Do something with someVar];
         } 
      });
      

      【讨论】:

        【解决方案4】:

        你可以使用 bool 变量来管理它

        $scope.someVarChanged = false;
        
        scope.$watch('someVar', function(newValue, oldValue) {
            console.log(newValue);
            $scope.someVarChanged = !$scope.someVarChanged!;
            if($scope.someVarChanged) {            
                scope.someVar = [Do something with someVar];
            }
        });
        

        【讨论】:

          【解决方案5】:

          当使用$scope.$watch 监视变量的更改时,角度检查引用是否已更改。如果有,则执行$watch 处理程序以更新视图。

          如果您计划在 $watch 处理程序中更改范围变量,它将触发无限的 $digest 循环,因为每次调用范围变量引用都会更改。

          解决无限摘要问题的技巧是使用 angular.copy (@ 987654321@):

          scope.$watch('someVar', function(newValue, oldValue) {
              console.log(newValue);
              var someVar = [Do something with someVar];
          
              // angular copy will preserve the reference of $scope.someVar
              // so it will not trigger another digest 
              angular.copy(someVar, $scope.someVar);
          
          });
          

          注意:此技巧仅适用于对象引用。它不适用于基元。

          一般来说,在自己的$watch 侦听器中更新$watched 变量不是一个好主意。但是,有时它可能是不可避免的。

          【讨论】:

            猜你喜欢
            • 1970-01-01
            • 1970-01-01
            • 1970-01-01
            • 2016-02-07
            • 1970-01-01
            • 1970-01-01
            • 1970-01-01
            • 1970-01-01
            • 1970-01-01
            相关资源
            最近更新 更多