淘汰赛性能-过滤可观察的阵列 [英] Knockout Performance - Filtering an Observable Array

查看:48
本文介绍了淘汰赛性能-过滤可观察的阵列的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我是Knockout的新手,我试图在显示系统用户以及每个用户具有的角色的页面上使用它.

I'm new to Knockout, and I'm trying to use it on a page showing a system's users and the roles that each user has.

数据在observableArray个用户中.用户对象具有一个Roles属性,这是另一个observableArray.第二个数组包含每个角色的对象,并带有ID和布尔"granted"属性.

The data is in an observableArray of users. The user object has a roles property, which is another observableArray. This second array contains an object for each role, with an ID and a boolean "granted" property.

我希望能够显示具有特定角色的所有用户,因此每个角色都有一个复选框-选中其中一个时,列表应显示具有该角色的用户.

I want to be able to display all of the users with a specific role, so there's a checkbox for each role - when one of these is checked, the list should show the users with that role.

我遇到的问题是按角色过滤1,000名左右的用户需要几秒钟.名称中的文本过滤非常快(几毫秒),但按角色过滤不是.我放入了一些计时代码,问题是我用来检查用户是否具有所选角色的方法,所以我只是想知道是否有更好的方法,也许可以使用一些Knockout魔术.

The problem I've got is that filtering the 1,000 or so users by roles takes several seconds. Filtering by the text in the name is very quick (a few milliseconds), but filtering by role is not. I've put some timing code in, and the issue is the method I'm using to check whether the user has the selected role(s) so I'm just wondering whether there's a better way of doing it, maybe using some Knockout magic.

下面是我用来进行过滤的视图模型上的ko.compute.结果表已绑定到此功能.

Below is the ko.computed on the view model that I'm using to do the filtering. The results table is bound to this function.

self.filteredUsers = ko.computed(function () {

    var textFilter = self.filter();          // this is an observable bound to a text field
    var checkedRoles = self.selectedRoles(); // this is a computed, which returns an array of checked roles

    return ko.utils.arrayFilter(self.users(), function (user) {

        var match = true;

        if (user.displayName.toLowerCase().indexOf(textFilter.toLowerCase()) == -1) {
            match = false;
        }

        // for each ticked role, check the user has the role
        for (var i = 0; i < checkedRoles.length; i++) {
            var roleMatch = false;
            for (var j = 0; j < user.roles().length; j++) {
                if (user.roles()[j].roleId === checkedRoles[i].roleId && user.roles()[j].granted()) {
                    roleMatch = true;
                    break;
                }
            }
            if (!roleMatch) {
                match = false;
            }
        }

        return match;
    });
});

推荐答案

我认为,一个好的优化方法是创建一个基于用户对象计算的grantedRoles.计算得出的结果将返回一个可用作索引的对象,将包含由角色的唯一标识符作为键的属性,并且仅包含被授予的角色.

I think that a good optimization would be creating a grantedRoles computed on your user object. This computed would return an object that you can use as an index, would contain properties keyed by a role's unique identifier and would only contain roles that are granted.

然后在filteredUsers中,您将针对每个选中的角色检查grantedRoles对象,而不是针对每个选中的角色循环遍历user.roles().

Then in filteredUsers, you would check the grantedRoles object against each checked role, rather than looping through user.roles() for each checked role.

这篇关于淘汰赛性能-过滤可观察的阵列的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆