创建按列分组的矩阵表

时间:2017-05-24 06:13:05

标签: javascript jquery html-table

我需要列出在特定区域内运行的所有项目。应将所有项目作为列添加到表中。项目数量可以增加,因此需要动态创建具有动态列的表。此外,表格应以两列开头,其中包括有关每个项目应重复的类别和区域的信息。我们还需要按状态对项目进行分组。所以我们需要列分组。我不知道下面的JSON结构是否准确无法满足要求,或者我们是否需要更改

我有类似的JSON,

[{
  "category": "a",
  "region": "Region 1",
  projects: [{
    "project": "A",
    "resources" : 2,
    "status": green
  }, {
    "project": "B", 
    "resources" : 2,
    "status": green
  }, {
    "project": "C",
    "resources" : 2,
    "status": green
  }]
}, {
  "category": "b",
  "region": "Region 2",
  projects: [{
    "project": "F",
    "resources" : 2,
    "status": red
  }, {
    "project": "A",
    "resources" : 4,
    "status": green
  }]
}]

是否可以动态创建按状态列分组的表。 或者我们应该从服务器端处理这些表的创建。 该表应该与此类似,



<table>
  <tr>
    <th rowspan="2">Category</th>
    <th rowspan="2">Region</th>
    <th colspan="4">Green</th>
    <th colspan="3">Red</th>
  </tr>
  <tr>
    <th>A</th>
    <th>B</th>
    <th>C</th>
    <th>D</th>
    <th>E</th>
    <th>F</th>
    <th>G</th>
  </tr>
  <tr>
    <td>A</td>
    <td>Region 1</td>
    <td>2</td>
    <td>2</td>
    <td>2</td>
    <td></td>
    <td></td>
    <td></td>
    <td></td>
  </tr>
  <tr>
    <td>B</td>
    <td>Region 2</td>
    <td>4</td>
    <td></td>
    <td></td>
    <td></td>
    <td></td>
    <td>2</td>
    <td></td>
  </tr>
  </table>
&#13;
&#13;
&#13;

我想是否可以使用上面的JSON结构通过jQuery动态实现,或者我们是否需要修改JSON结构。

1 个答案:

答案 0 :(得分:1)

您可以使用

等功能在JavaScript中执行此操作
"use strict";

function groupBy(array, selectKey) {
  return array.reduce((groups, element) => {
      const key = selectKey(element);
      if (groups[key]) {
        groups[key].push(element);
      } 
      else {
        groups[key] = [element];
      }

      return groups;
    }, {});
}

这会将数组投影到一个对象中,该对象具有从数组中的对象投射的每个不同键的属性。每个属性的值将是在我们传递的任何selectKey函数下生成该键的值的数组。

注意:selectKey应该返回一个字符串或数字,无论如何,它的结果将被强制转换为字符串。

现在,根据您的阵列,我们可以对其进行分组。

让我们从category分组开始:

"use strict";

function groupBy(array, selectKey) {
  return array.reduce((groups, element) => {
      const key = selectKey(element);
      if (groups[key]) {
        groups[key].push(element);
      } 
      else {
        groups[key] = [element];
      }
      
      return groups;
    }, {});
}

const xs = [{
  "category": "a",
  "region": "Region 1",
  projects: [{
    "project": "A",
    "resources": 2,
    "status": 'green'
  }, {
    "project": "B",
    "resources": 2,
    "status": 'green'
  }, {
    "project": "C",
    "resources": 2,
    "status": 'green'
  }]
}, {
  "category": "b",
  "region": "Region 2",
  projects: [{
    "project": "F",
    "resources": 2,
    "status": 'red'
  }, {
    "project": "A",
    "resources": 4,
    "status": 'green'
  }]
}];

const byCategory = groupBy(xs, x => x.category);

console.log(byCategory);

现在,如果我们需要按多列分组呢?我们可以使用逻辑来扩充groupBy以获取自定义比较函数,但我们可以通过使用字符串连接来作弊。

在以下示例中,我们按category 分组region

"use strict";

function groupBy(array, selectKey) {
  return array.reduce((groups, element) => {
      const key = selectKey(element);
      if (groups[key]) {
        groups[key].push(element);
      } 
      else {
        groups[key] = [element];
      }
      
      return groups;
    }, {});
}

const xs = [{
  "category": "a",
  "region": "Region 1",
  projects: [{
    "project": "A",
    "resources": 2,
    "status": 'green'
  }, {
    "project": "B",
    "resources": 2,
    "status": 'green'
  }, {
    "project": "C",
    "resources": 2,
    "status": 'green'
  }]
}, {
  "category": "b",
  "region": "Region 2",
  projects: [{
    "project": "F",
    "resources": 2,
    "status": 'red'
  }, {
    "project": "A",
    "resources": 4,
    "status": 'green'
  }]
}];

const byCategoryAndRegion = groupBy(
    xs,
    x => `category: ${x.category}, region: ${x.region}`
  );

console.log(byCategoryAndRegion);

我对数据的结构和方向并不完全清楚,但这应该足以让你前进。