【问题标题】:Group the objects by Board name按 Board 名称对对象进行分组
【发布时间】:2020-12-28 02:44:33
【问题描述】:

我有一个很长的 JSON,它是一个对象数组。每个元素都有属性 name 和 boards。我需要根据董事会名称将他们加入俱乐部。

[
  {
    "name": "school education",
    "boards": [
      {
        "name": "CBSE",
        "grades": [
          {
            "name": "class 1",
            "subject": [
              "french"
            ]
          }
        ]
      }
    ]
  },
  {
    "name": "school education",
    "boards": [
      {
        "name": "CBSE",
        "grades": [
          {
            "name": "class 1",
            "subject": [
              "physical education"
            ]
          }
        ]
      }
    ]
  },
  {
    "name": "school education",
    "boards": [
      {
        "name": "CBSE",
        "grades": [
          {
            "name": "class 1",
            "subject": [
              "chinese"
            ]
          }
        ]
      }
    ]
  },
  {
    "name": "school education",
    "boards": [
      {
        "name": "CBSE",
        "grades": [
          {
            "name": "class 1",
            "subject": [
              "sanskrit"
            ]
          }
        ]
      }
    ]
  },
  {
    "name": "school education",
    "boards": [
      {
        "name": "CBSE",
        "grades": [
          {
            "name": "class 1",
            "subject": [
              "spanish"
            ]
          }
        ]
      }
    ]
  },
  {
    "name": "school education",
    "boards": [
      {
        "name": "CBSE",
        "grades": [
          {
            "name": "class 1",
            "subject": [
              "russian"
            ]
          }
        ]
      }
    ]
  },
  {
    "name": "school education",
    "boards": [
      {
        "name": "JKBOSE",
        "grades": [
          {
            "name": "class 1",
            "subject": [
              "french"
            ]
          }
        ]
      }
    ]
  },
  {
    "name": "school education",
    "boards": [
      {
        "name": "JKBOSE",
        "grades": [
          {
            "name": "class 1",
            "subject": [
              "physical education"
            ]
          }
        ]
      }
    ]
  },
  {
    "name": "school education",
    "boards": [
      {
        "name": "JKBOSE",
        "grades": [
          {
            "name": "class 1",
            "subject": [
              "chinese"
            ]
          }
        ]
      }
    ]
  },
  {
    "name": "school education",
    "boards": [
      {
        "name": "JKBOSE",
        "grades": [
          {
            "name": "class 1",
            "subject": [
              "sanskrit"
            ]
          }
        ]
      }
    ]
  },
  {
    "name": "school education",
    "boards": [
      {
        "name": "JKBOSE",
        "grades": [
          {
            "name": "class 1",
            "subject": [
              "spanish"
            ]
          }
        ]
      }
    ]
  },
  {
    "name": "school education",
    "boards": [
      {
        "name": "JKBOSE",
        "grades": [
          {
            "name": "class 1",
            "subject": [
              "russian"
            ]
          }
        ]
      }
    ]
  }
]

我有上面的 JSON,我需要将它转换成这种格式。所以我的 JSON 现在将有一个 name 键,它由

组成

学校教育 和其他关键的板,它们将根据名称对所有项目进行分组。

name: "school education",
    boards: [
      {
        name: "CBSE",
        grades: [
          {
            name: "Class 1",
            subjects: ["Maths", "Hindi", "EVS", "English"]
          },
          {
            name: "Class 2",
            subjects: ["Maths", "Hindi", "EVS", "English"]
          },
          {
            name: "Class 3",
            subjects: ["Maths", "Hindi", "EVS", "English"]
          },
          {
            name: "Class 4",
            subjects: ["Maths", "Hindi", "EVS", "English"]
          },
          {
            name: "Class 5",
            subjects: ["Maths", "Hindi", "EVS", "English"]
          },
          {
            name: "Class 6",
            subjects: [
              "Maths",
              "Hindi",
              "English",
              "History",
              "Geography",
              "Civics",
              "Sanskrit",
              "Science"
            ]
          },

【问题讨论】:

  • 到目前为止你有什么尝试?

标签: javascript arrays json arraylist lodash


【解决方案1】:

您实际上所做的是在每个级别进行分组和映射。

您需要按项目名称分组;然后在每个项目中,按板分组;在每个板上,按等级分组。对于每个嵌套项目,这变得更加复杂。

const main = () => {
  const result = _.chain(data())
    .groupBy('name')
    .map((value1, key1) => ({
      name: key1,
      boards: _.chain(value1)
        .groupBy('boards[0].name')
        .map((value2, key2) => ({
          name: key2,
          grades: _.chain(value2)
            .groupBy('boards[0].grades[0].name')
            .map((value3, key3) => ({
              name: value3[0].boards[0].grades[0].name,
              subjects: _.flattenDeep(value3.map(item => {
                return item.boards.map(board => {
                  return board.grades.map(grade => {
                    return grade.subject;
                  })
                })
              }))
            }))
        }))
    }))
    .value();
    
  console.log(result);
};

const data = () => [{
  "name": "school education",
  "boards": [{
    "name": "CBSE",
    "grades": [{
      "name": "class 1",
      "subject": ["french"]
    }]
  }]
}, {
  "name": "school education",
  "boards": [{
    "name": "CBSE",
    "grades": [{
      "name": "class 1",
      "subject": ["physical education"]
    }]
  }]
}, {
  "name": "school education",
  "boards": [{
    "name": "CBSE",
    "grades": [{
      "name": "class 1",
      "subject": ["chinese"]
    }]
  }]
}, {
  "name": "school education",
  "boards": [{
    "name": "CBSE",
    "grades": [{
      "name": "class 1",
      "subject": ["sanskrit"]
    }]
  }]
}, {
  "name": "school education",
  "boards": [{
    "name": "CBSE",
    "grades": [{
      "name": "class 1",
      "subject": ["spanish"]
    }]
  }]
}, {
  "name": "school education",
  "boards": [{
    "name": "CBSE",
    "grades": [{
      "name": "class 1",
      "subject": ["russian"]
    }]
  }]
}, {
  "name": "school education",
  "boards": [{
    "name": "JKBOSE",
    "grades": [{
      "name": "class 1",
      "subject": ["french"]
    }]
  }]
}, {
  "name": "school education",
  "boards": [{
    "name": "JKBOSE",
    "grades": [{
      "name": "class 1",
      "subject": ["physical education"]
    }]
  }]
}, {
  "name": "school education",
  "boards": [{
    "name": "JKBOSE",
    "grades": [{
      "name": "class 1",
      "subject": ["chinese"]
    }]
  }]
}, {
  "name": "school education",
  "boards": [{
    "name": "JKBOSE",
    "grades": [{
      "name": "class 1",
      "subject": ["sanskrit"]
    }]
  }]
}, {
  "name": "school education",
  "boards": [{
    "name": "JKBOSE",
    "grades": [{
      "name": "class 1",
      "subject": ["spanish"]
    }]
  }]
}, {
  "name": "school education",
  "boards": [{
    "name": "JKBOSE",
    "grades": [{
      "name": "class 1",
      "subject": ["russian"]
    }]
  }]
}];

main();
.as-console-wrapper { top: 0; max-height: 100% !important; }
<script src="https://cdnjs.cloudflare.com/ajax/libs/lodash.js/4.17.20/lodash.min.js"></script>

或者,这就是你可以在没有库的情况下做到这一点的方法。

const main = () => {
  const nameGroups = data().reduce((result, item) => {
    return {
      ...result,
      [item.name]: [ ...(result[item.name] || []), item.boards ]
    }
  }, {});
  const result = Object.keys(nameGroups).map(key => {
    const boardGroups = nameGroups[key].flat().reduce((result, board) => {
      return {
        ...result,
        [board.name]: [ ...(result[board.name] || []), board.grades ]
      }
    }, {});
    return {
      name: key,
      boards: Object.keys(boardGroups).map(board => {
        const gradeGroups = boardGroups[board].flat().reduce((res, grade) => {
          return {
            ...res,
            [grade.name]: [ ...(res[grade.name] || []), grade.subject ].flat()
          }
        }, {});
        return {
          name: board,
          grades: Object.keys(gradeGroups).map(key => {
            return {
              name: key,
              subjects: gradeGroups[key]
            }
          })
        }
      })
    }
  });
  
  console.log(result);
};

const data = () => [{
  "name": "school education",
  "boards": [{
    "name": "CBSE",
    "grades": [{
      "name": "class 1",
      "subject": ["french"]
    }]
  }]
}, {
  "name": "school education",
  "boards": [{
    "name": "CBSE",
    "grades": [{
      "name": "class 1",
      "subject": ["physical education"]
    }]
  }]
}, {
  "name": "school education",
  "boards": [{
    "name": "CBSE",
    "grades": [{
      "name": "class 1",
      "subject": ["chinese"]
    }]
  }]
}, {
  "name": "school education",
  "boards": [{
    "name": "CBSE",
    "grades": [{
      "name": "class 1",
      "subject": ["sanskrit"]
    }]
  }]
}, {
  "name": "school education",
  "boards": [{
    "name": "CBSE",
    "grades": [{
      "name": "class 1",
      "subject": ["spanish"]
    }]
  }]
}, {
  "name": "school education",
  "boards": [{
    "name": "CBSE",
    "grades": [{
      "name": "class 1",
      "subject": ["russian"]
    }]
  }]
}, {
  "name": "school education",
  "boards": [{
    "name": "JKBOSE",
    "grades": [{
      "name": "class 1",
      "subject": ["french"]
    }]
  }]
}, {
  "name": "school education",
  "boards": [{
    "name": "JKBOSE",
    "grades": [{
      "name": "class 1",
      "subject": ["physical education"]
    }]
  }]
}, {
  "name": "school education",
  "boards": [{
    "name": "JKBOSE",
    "grades": [{
      "name": "class 1",
      "subject": ["chinese"]
    }]
  }]
}, {
  "name": "school education",
  "boards": [{
    "name": "JKBOSE",
    "grades": [{
      "name": "class 1",
      "subject": ["sanskrit"]
    }]
  }]
}, {
  "name": "school education",
  "boards": [{
    "name": "JKBOSE",
    "grades": [{
      "name": "class 1",
      "subject": ["spanish"]
    }]
  }]
}, {
  "name": "school education",
  "boards": [{
    "name": "JKBOSE",
    "grades": [{
      "name": "class 1",
      "subject": ["russian"]
    }]
  }]
}];

main();
.as-console-wrapper { top: 0; max-height: 100% !important; }

【讨论】:

    【解决方案2】:

    您可以使用一种简洁的方法,循环到子数组的键的级别,并为每个级别使用递归。

    function groupBy(source, [key, ...keys], target = []) {
        const
            group = ({ name, [key]: values }) => {
                let item = target.find(q => q.name === name);
                if (!item) target.push(item = { name, [key]: [] });
                groupBy(values, keys, item[key]);
            };
    
        if (key) source.forEach(group);
        else target.push(...source);
    
        return target;
    }
    
    const
        data = [{ name: "school education", boards: [{ name: "CBSE", grades: [{ name: "class 1", subject: ["french"] }] }] }, { name: "school education", boards: [{ name: "CBSE", grades: [{ name: "class 1", subject: ["physical education"] }] }] }, { name: "school education", boards: [{ name: "CBSE", grades: [{ name: "class 1", subject: ["chinese"] }] }] }, { name: "school education", boards: [{ name: "CBSE", grades: [{ name: "class 1", subject: ["sanskrit"] }] }] }, { name: "school education", boards: [{ name: "CBSE", grades: [{ name: "class 1", subject: ["spanish"] }] }] }, { name: "school education", boards: [{ name: "CBSE", grades: [{ name: "class 1", subject: ["russian"] }] }] }, { name: "school education", boards: [{ name: "JKBOSE", grades: [{ name: "class 1", subject: ["french"] }] }] }, { name: "school education", boards: [{ name: "JKBOSE", grades: [{ name: "class 1", subject: ["physical education"] }] }] }, { name: "school education", boards: [{ name: "JKBOSE", grades: [{ name: "class 1", subject: ["chinese"] }] }] }, { name: "school education", boards: [{ name: "JKBOSE", grades: [{ name: "class 1", subject: ["sanskrit"] }] }] }, { name: "school education", boards: [{ name: "JKBOSE", grades: [{ name: "class 1", subject: ["spanish"] }] }] }, { name: "school education", boards: [{ name: "JKBOSE", grades: [{ name: "class 1", subject: ["russian"] }] }] }],
        result = groupBy(data, ['boards', 'grades', 'subject']);
       
    console.log(result);
    .as-console-wrapper { max-height: 100% !important; top: 0; }

    【讨论】:

      猜你喜欢
      • 2012-05-23
      • 2022-06-22
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2020-10-11
      • 2022-01-03
      相关资源
      最近更新 更多