Warning: file_get_contents(/data/phpspider/zhask/data//catemap/8/meteor/3.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
angularjs指令:$rootScope:infdig错误_Angularjs_Angularjs Directive - Fatal编程技术网

angularjs指令:$rootScope:infdig错误

angularjs指令:$rootScope:infdig错误,angularjs,angularjs-directive,Angularjs,Angularjs Directive,我正在尝试使用angularjs 1.2.15构建分页指令: 我的看法是: <input type="text" ng-model="filter.user"> <input type="number" ng-model="filter.limit" ng-init="filter.limit=5"> <ul> <li ng-repeat="user in (filteredUsers = (users | orderBy:order:reverse

我正在尝试使用angularjs 1.2.15构建分页指令:

我的看法是:

<input type="text" ng-model="filter.user">
<input type="number" ng-model="filter.limit" ng-init="filter.limit=5">
<ul>
  <li ng-repeat="user in (filteredUsers = (users | orderBy:order:reverse | filter:filter.user ) | limitTo: filter.limit)" ng-click="showDetails(user)">
    {{user.id}} / {{user.firstname}} {{user.lastname}}
  </li>
</ul>
<div pagination data='filteredUsers' limit='filter.limit'></div>
没有分页指令,一切都可以正常工作。然而,使用我的新指令,当我加载页面时,我会得到一个
$rootScope:infdig
错误,我不理解这个错误,因为该指令没有做任何操作来处理可能最终进入无限循环的数据。
这里的问题是什么?我该如何解决?谢谢

更新:
这是控制器和资源。
控制器:

usersModule.controller('usersController',
  function ($scope, Users) {
    function init(){
      $scope.users = Users.get();
    }
    init();
})
资源(从REST API以数组形式获取用户):

更新2

这里有一个演示:

只需在左侧输入中键入一个字母(如“f”)。

问题不在指令范围内,而是在指令创建的$watch范围内。 向指令发送filteredUsers时,指令将创建以下行:

$scope.$watch("filteredUsers", function() {
    // Directive Code...
});
请注意,在下面的示例中,我们如何在没有指令的情况下复制它:

之所以会发生这种情况,是因为每次摘要运行时都要更改filteredUsers(因为您将赋值放在ng repeat语句中)

为了解决这个问题,您可以考虑在控制器中查看和筛选数组,并使用额外的参数“true”来监视$:

$scope.$watch("users | orderBy:order:reverse | filter:filter.user", function(newVal) {
    $scope.filteredUsers = newVal;
}, true);
您可以在此处检查解决方案:

不带额外参数(true)的$watch将与对象进行简单比较,并且由于您在每个摘要循环中创建了一个新数组,因此对象总是不同的。 当您将真正的参数传递给$Watch函数时,这意味着它实际上会与在再次运行$Catch之前返回的对象进行深入的比较,因此即使有相同数据的数组的不同实例,它也会认为它们是相等的。

< P>快速修复是添加一个“手册”。指令中的
$watchCollection
,而不是双向绑定

app.directive('pagination', function($parse){
  return {
    restrict: 'A',
    template: '',
    scope: {
      limit: '=limit'
    },
    link: function(scope, elem, attrs) {
      var dataExpr = $parse(attrs.data);
      var deregister = scope.$parent.$watchCollection(dataExpr, function(val) {
        scope.data = val;
      });
      scope.$on('$destroy', deregister);
    }
  }
})
$watchCollection
监视数组的内容,而不是对数组的引用

看到它在运行

一般来说,我不喜欢这样的表达:

filteredUsers = (users | orderBy:order:reverse | filter:filter.user )

内部视图。视图应仅呈现
$scope
属性,而不创建新属性。

此错误可能会删除,以从设置中清除浏览器历史记录。我遇到了同样的问题,并应用了许多解决方案来解决这个问题,但无法解决。
但当我删除浏览器历史记录并缓存时,这个问题就解决了。愿这对你有帮助

请为控制器指定代码,以便人们能够接触到问题。我认为上述指令是完美的。您的控制器可能有问题。@JenishRabadiya我更新了上面的代码。但是,我不认为这与我的控制器有任何关系……顺便说一句,当将
用户
而不是
过滤器用户
传递到指令中时,不会发生错误…@Horen:这种情况很好地解决了(节省了每个人的时间):@Horen:显然这是您的分页模板中的一些内容,因此,分享这些可能也会有所帮助……是的,这似乎解决了问题。不过,我不太明白为什么第一个示例中的
$watch()
函数会改变任何东西。我知道它是在应用或更改过滤器时触发的。但是,
$watch()
函数甚至不会以任何方式操作或更改
filteredUsers
对象。那么无限循环是如何产生的呢?即使
$watch()
函数使用每个
摘要创建一个新对象,这个对象也不应该更改,对吗?如果你能澄清,那就太好了-谢谢你!由于在ng repeat语句中创建变量filteredUsers-语句为:filteredUsers=(users | orderBy:order:reverse | filter:filter.user),这意味着在每个摘要周期中,filteredUsers都会获得一个新的对象引用。当您使用$watch方法时,它会检查引用是否已更改,如果已更改,它会将手表视为“脏”,运行注册到它的回调方法,然后再次运行摘要循环-在下一个摘要循环中,filteredUsers将再次更改,因此将再次调用$watch回调-这是您的无限循环…好的,谢谢。但是,为什么在
init()
函数中声明一次
$scope.filteredUsers
对象还不够?我的意思是,angular应该知道它总是同一个对象,对吧?好吧,如果你使用
$scope.filteredUsers=[1,2,3]
例如,它将定义一个新数组,并且每当你在其中更改一个值时,它不会触发一个简单的手表(像
$scope.filteredUsers[0]=5这样更改)但是,如果为整个变量指定一个新值,它会发生变化,例如
$scope.filteredUsers=[5,2,3]
将触发一个监视。在控制台中尝试以下行,您将看到它返回false:
[5,2,3]===[5,2,3]
。但是如果你尝试
a1=[1,2,3];a2=a1;a1[0]=5
您将看到
a1==a2
返回true。在
ng repeat
中,您总是创建一个新实例。我遇到了类似的问题。我添加了
ng-clope
,以查看元素的一部分。它解决了这个问题。我不明白这在隔离作用域中是如何工作的。隔离作用域如何才能正确计算
attrs.data
表达式?@nicolaseurdu,你说得对。您必须在父作用域上注册监视,并在子作用域终止时取消注册。我编辑了代码。
app.directive('pagination', function($parse){
  return {
    restrict: 'A',
    template: '',
    scope: {
      limit: '=limit'
    },
    link: function(scope, elem, attrs) {
      var dataExpr = $parse(attrs.data);
      var deregister = scope.$parent.$watchCollection(dataExpr, function(val) {
        scope.data = val;
      });
      scope.$on('$destroy', deregister);
    }
  }
})
filteredUsers = (users | orderBy:order:reverse | filter:filter.user )