在AngularJS中对对象数组进行分组

3

基于这样的数组:

var members = [
  {name: "john", team: 1},
  {name: "kevin", team: 1},
  {name: "rob", team: 2},
  {name: "matt", team: 2},
  {name: "clint", team: 3},
  {name: "will", team: 3}
];

我需要为每个团队创建一个无序列表。

是否可以直接使用ngRepeat和过滤器完成?

或者将数组重新组织成一个团队数组,其中包含成员列表,这样更容易实现吗?

var teams = [
  {id: 1, members: ["john", "kevin"]},
  {id: 2, members: ["rob", "matt"]},
  {id: 3, members: ["clint", "will"]}
]

嵌套的ngRepeat很容易实现,但我该如何以简单/巧妙的方式从第一个数组过渡到这个数组呢?

注意:这个数组不是来自数据库,而是来自html表格。所以它只是成员的一个平面列表。

function MyController() {
  this.members = [
    {name: "john", team: 1},
    {name: "kevin", team: 1},
    {name: "rob", team: 2},
    {name: "matt", team: 2},
    {name: "clint", team: 3},
    {name: "will", team: 3}
  ];
}

angular.module('app', []);
angular.module('app')
    .controller('MyController', MyController);
<script src="https://ajax.googleapis.com/ajax/libs/angularjs/1.6.3/angular.min.js"></script>
<div ng-app="app">
  <div ng-controller="MyController as ctrl">
    <ul>
      <li ng-repeat="member in ctrl.members">{{ member.name }} - {{ member.team }}</li>
    </ul>
  </div>
</div>


这个链接也许会对你有所帮助:https://dev59.com/YmUq5IYBdhLWcg3wF8hQ - Muhammad Ramzan
5个回答

13

你需要对项目进行分组。为此,我使用了reduce方法来创建一个类似于这样的hash集合:

{
  "1": [
    "john",
    "kevin"
  ],
  "2": [
    "rob",
    "matt"
  ],
   "3": [
     "clint",
      "will"
   ]
}

reduce() 方法对数组中的每个元素(从左到右)应用一个函数,将其缩减为单个值。

下一步是把这个集合map成一个array。 为此,您应该使用map方法。

map() 方法调用数组中的每个元素上执行提供的函数,并使用执行结果创建一个新的数组。

var members = [
  {name: "john", team: 1},
  {name: "kevin", team: 1},
  {name: "rob", team: 2},
  {name: "matt", team: 2},
  {name: "clint", team: 3},
  {name: "will", team: 3}
];
var groups = members.reduce(function(obj,item){
    obj[item.team] = obj[item.team] || [];
    obj[item.team].push(item.name);
    return obj;
}, {});
var myArray = Object.keys(groups).map(function(key){
    return {team: key, name: groups[key]};
});
console.log(myArray);


2
我会选择这个答案而不是过滤器。这样我就可以将转换后的数组直接传递给服务。 - gyc

6

扩展@Alexandru-Ionut Mihai的答案,(只是为了体验一下reduce函数的强大)..这里有一个单独的reduce,而不需要再次map它来实现相同的功能。 :)

var members = [
  {name: "john", team: 1},
  {name: "kevin", team: 1},
  {name: "rob", team: 2},
  {name: "matt", team: 2},
  {name: "clint", team: 3},
  {name: "will", team: 3}
];
/*var teams = [
  {id: 1, members: ["john", "kevin"]},
  {id: 2, members: ["rob", "matt"]},
  {id: 3, members: ["clint", "will"]}
]*/
var group_to_values = members.reduce(function(arr, item){
    arr[item.team - 1] = arr[item.team - 1] || { id: item.team, members: []};
    arr[item.team - 1].members.push(item.name);
    return arr;
}, []);

console.log(group_to_values);


3
如果您正在使用underscore.js,则可以使用_.groupBy()方法根据团队对记录数组进行分组。
function MyController() {
  this.members = [
    {name: "john", team: 1},
    {name: "kevin", team: 1},
    {name: "rob", team: 2},
    {name: "matt", team: 2},
    {name: "clint", team: 3},
    {name: "will", team: 3}
  ];

var grouped = _.groupBy(this.members, function(member) {
  return member.team;
});
}

2
您可以使用类似于以下示例的groupBy筛选器。
<ul ng-repeat="(key, value) in members | orderBy: 'team' | groupBy:ourGrouper">
      <li>{{key}}
        <ul>
          <li ng-repeat="mem in value | orderBy: 'name'">
            {{mem.name}}
          </li>
        </ul>
      </li>
    </ul>

请查看此示例代码。它涉及IT技术。

1

var members = [
  {name: "john", team: 1},
  {name: "kevin", team: 1},
  {name: "rob", team: 2},
  {name: "matt", team: 2},
  {name: "clint", team: 3},
  {name: "will", team: 3}
];
var groups = members.reduce(function(obj,item){
    obj[item.team] = obj[item.team] || [];
    obj[item.team].push(item.name);
    return obj;
}, {});
var myArray = Object.keys(groups).map(function(key){
    return {team: key, name: groups[key]};
});
console.log(myArray);


网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接