自定义过滤器与控制器性能比较中的过滤功能

假设我有一个包含5000个对象(带有布尔值)的数组,我必须在模板中ng-repeat

$scope.arr = [
    {
        "value": true
    },
    {
        "value": false
    },
    {
        "value": false
    }
    //and so on
]

现在,我想根据一个动态变量过滤这个ng-repeated数组,比如我在其他地方设置的'show_filter'。

如果'show_filter'被设置为'all',我想显示所有的对象。 如果它设置为false(布尔值),那么我想显示'value'键设置为false的对象。 当'show_filter'设置为true时也是如此。

所以有两种方法:

1.建立一个自定义过滤器:

我会为过滤任务编写一个自定义过滤器,如下所示:

过滤:

app.filter('filterArr', function() {
    return function(arr, show_filter) {
        var filtered_arr = [];
        if(show_filter != 'All') { //if show_filter is a boolean value
            for(var i = 0; i < arr.length; i++) {
                if(arr[i].value == show_filter) { 
                    filtered_arr.push(arr[i]);
                }
            }
            return filtered_arr;
        }
        else {
            return arr; //return the entire array if show_filter is set to 'All'
        }
    }
})

模板:

obj in arr | filterArr : show_filter

2.在控制器中写入过滤器功能:

过滤:

$scope.filterObjects = function(arr) {
    var filtered_arr = [];
    if($scope.show_filter != 'All') { //if $scope.show_filter is a boolean value
        for(var i = 0; i < arr.length; i++) {
            if(arr[i].value == $scope.show_filter) { 
                filtered_arr.push(arr[i]);
            }
        }
        return filtered_arr;
    }
    else {
        return arr; //return the entire array if show_filter is set to 'All'
    }
}

模板:

obj in filterObjects(arr)

上述两种方法中的哪一种会更快? 我已经看到每个digest循环每次都执行自定义过滤器代码,而不仅仅是对$scope.show_filter所做的更改,这使我相信它效率非常低。 虽然我不确定两种方式之间哪个更快。


这两个函数都将在每个摘要循环中调用。 对于第二个功能来说这很明显。 filterObjects(arr)的返回值在每次调用时都可能不同。

为什么在每个摘要循环中会调用一个过滤器并不是很明显。 该文档声明如下:

过滤器函数应该是一个纯函数,这意味着它应该是无状态和幂等的。 Angular依赖于这些属性,并且只有在函数的输入发生变化时才执行过滤器。

因此,如果arrshow_filter更改,那么不应该调用过滤器,对吧? 但是这里有一个问题:检测arr的变化是很昂贵的。

Angular必须复制数组以将其与当前内容进行比较。 即使没有任何变化,每一个项目都必须进行比较。 如果这些项目是对象的每一个属性都必须进行比较。 直接调用过滤器会更便宜。 这就是当一个过滤器应用于数组(或对象)时Angular所做的事情。

为了加速应用程序,你有两个选择。 第一种是仅在必要时过滤数组,并将过滤的数组暴露给ng-repeat 。 例如,如果您可以输入一个数值将被过滤,那么只要该值发生变化就过滤该数组。

如果数组和过滤器都没有改变,那么可以使用第二种选择(所以不适用于你的情况)。 然后你可以使用一次性绑定:

<li ng-repeat="item in ::array | filter">

当你有一组固定的项目并想按名称对它们进行排序时,这很有用,例如,在这种情况下,过滤器只会被调用一次。

链接地址: http://www.djcxy.com/p/88953.html

上一篇: Custom filter vs filter function in controller performance comparison

下一篇: How to create digital object identifier (DOI) for bitbucket repository?