【问题标题】:How to filter the JSON data using AngularJS?如何使用 AngularJS 过滤 JSON 数据?
【发布时间】:2016-11-08 08:27:23
【问题描述】:

我有三个dropdown 框。我需要过滤数据并需要根据我的复选框选择显示在表格中(single checkbox 或two checkboxes 或three checkboxes)。

我做了以下,但如果我们观察清楚,我无法使用AngularJS正确过滤数据。

喜欢:

一个。它应该适用于individual checkbox selection:意味着如果我从Name或Description或Field4中选择任何single checkbox,则相应的匹配过滤数据应显示在表格中,否则不应显示任何数据(即如果它不匹配我们的复选框选择意味着它不会显示任何数据)

b.它应该适用于multiple(two) checkbox selection:意味着如果我选择任何多个复选框,例如one from Name和one from Descriptionorone from Description和one from Field4orone from Field4和one from Name,然后分别匹配过滤数据应该显示在表格中,否则不应该显示任何数据(即如果它不匹配我们的复选框选择意味着它不会显示任何数据)

c。它应该适用于multiple(three) checkbox selection:意味着如果我选择one from Name和one from Description和one from Field4等三个复选框,则相应匹配的过滤数据应显示在表格中,否则不应显示任何数据(即如果它不匹配我们的复选框选择意味着它不会显示任何数据)

它第一次工作正常checkbox仅选择,意味着:在加载上述代码/应用程序后,如果我们check上述任何一个选择(如single checkbox选择或two checkbox选择或three checkbox选择)然后它工作正常,后来它不起作用(意味着如果我们uncheck上述任何标准,然后如果我们再次选择任何checkbox那么它不起作用,为此我们需要再次刷新应用程序/代码只有它在工作)。

示例:如果我从名称中选择一个,则将显示相应的匹配数据。再说一次,如果我uncheck 和check 相同,some other checkbox 就像来自Description 一样,那么它就不起作用了。对于上述所有标准也是如此。你可以observe看清楚。

请让我知道我在这里做错了什么,并让我知道如何正确过滤它。创建Fiddle。提前致谢!

【问题讨论】:

  • 您的小提琴似乎按照您指定的方式工作。没有按预期工作的行为是什么?
  • @LarryTurtis,如果我们清楚地观察,它只在第一次选择复选框时工作正常,即如果我们检查上述任何一个选择(比如是单个复选框选择还是两个复选框选择或三个复选框选择)然后它工作正常,后来它不工作(即,如果我们取消选中上述任何条件,然后如果我们再次选择任何复选框,那么它就不起作用,为此我们需要再次刷新代码然后它才工作) .
  • @LarryTurtis,示例:如果我从名称中选择一个,则将显示相应的匹配数据。然后再次如果我取消选中并选中相同的复选框,那么它不起作用。你可以清楚地观察它。
  • @LarryTurtis,示例:如果我从名称中选择一个,则将显示相应的匹配数据。然后,如果我取消选中相同的复选框并选中其他复选框,比如来自描述,那么它就不起作用了。对于上述所有标准也是如此。你可以清楚地观察它

标签: angularjs json angularjs-ng-repeat angular-filters angularjs-1.5


【解决方案1】:

问题在于复杂的过滤逻辑。每当您发现自己嵌套了很多 if 语句时,请考虑重新组织分支逻辑。通过将其分解为更小的组件,您可以使其更易于管理,如果您可以完全避免使用if,那么您只需测试一条路径,而不是多条路径。

每次用户选中一个框时,我们都需要确保只显示匹配的项目,无论选中了多少个框。所以我们需要知道 1) 选中了多少个框,n,以及 2) 通过 n 个匹配字段可以找到多少个项目。

我们可以利用布尔变量可以转换为整数(0 = false,true = 1)这一事实,并使用它来计算选中框的数量以及找到的匹配项的数量。

我们也可以把字段名放到一个数组中,这样我们的函数就不会有太多的重复了。

Fiddle example here.

var fields = ["name", "description", "field4"];

//for each field, count how many fields the item matches
function getMatches(item, matchesNeeded) {
    var foundMatches = 0;
    fields.forEach(field => {
      foundMatches += item[field] === $scope.pagedItems[field]
    });

    //make sure found at least one match and found desired minimum
    return foundMatches && foundMatches >= matchesNeeded;
}

//count how many boxes are checked
//this will tell us how many different fields we are matching on
function numChecked() {
    var count = 0;
    fields.forEach(field => {
        //this will auto convert falsy to 0.
        //truthy values will be 1
        count += Boolean($scope.pagedItems[field]);
    });
    return count;
}

$scope.filterItems = function(item) {
    return getMatches(item, numChecked());
};

【讨论】:

  • 是的,它按预期工作正常!感谢您的帮助!
【解决方案2】:

正如@Larry 指出的那样,它更多地基于逻辑。为此,我修改了 Apress 书 'Pro AngularJS' Source Code from GIT。

过滤功能中的基本逻辑如下-

$scope.categoryFilterFn = function (product) {
    var canHave = false;//dont load by default
    var atLeastOneTrue = false;//Check if previously checked any condition
    angular.forEach(filterValues, function(selectedValue, key) {
        var selectVals = Object.values(selectedValue);
            if(selectVals.indexOf(product[key]) !== -1) {//if values exits in product.
                canHave = !atLeastOneTrue ? true : canHave;
            }else{
                canHave = false;
            }
            atLeastOneTrue = true;
    });
    return canHave;
}

对于working Fiddle。

【讨论】:

  • 感谢您的回复,是的,它也按预期工作正常,但我也需要排序。感谢您的支持!
猜你喜欢
  • 2012-08-09
  • 1970-01-01
  • 1970-01-01
  • 2017-03-29
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2014-08-14
相关资源
最近更新 更多