如何按年份升序、月份顺序重新排序数组对象(保留首元素)
数组对象排序问题
原始数组对象如下:
var dataset = [ { "data" : "Country", "title" : "country" }, { "data" : "Jan 2023", "title" : "Jan 2023" }, { "data" : "Feb 2023", "title" : "Feb 2023" }, { "data" : "Dec 2022", "title" : "Dec 2022" }, ]
需求:保留第一个元素("Country"项)不变,其余元素按年份升序排列,同年份按月份顺序排列,最终结果如下:
var dataset = [ { "data" : "Country", "title" : "country" }, { "data" : "Dec 2022", "title" : "Dec 2022" }, { "data" : "Jan 2023", "title" : "Jan 2023" }, { "data" : "Feb 2023", "title" : "Feb 2023" }, ]
之前尝试的排序代码未达预期:
var newdataset = dataset.sort((a, b) => { if (a !== columns[0] && b !== columns[0]) { return b.data.length - a.data.length } })
解决方案
问题分析
之前的代码逻辑存在两处关键问题:
- 对象引用比较(
a !== columns[0])不严谨,容易因对象实例不同导致判断失效; - 用字符串长度比较完全无法实现按年月排序的需求,逻辑方向错误。
正确实现代码
// 提取第一个元素,剩余元素单独处理 const firstItem = dataset[0]; const restItems = dataset.slice(1); // 定义月份映射表,将缩写转为数字用于排序 const monthMap = { 'Jan': 1, 'Feb': 2, 'Mar': 3, 'Apr': 4, 'May': 5, 'Jun': 6, 'Jul': 7, 'Aug': 8, 'Sep': 9, 'Oct': 10, 'Nov': 11, 'Dec': 12 }; // 对剩余元素执行排序 restItems.sort((a, b) => { // 拆分日期字符串为月份和年份 const [aMonth, aYear] = a.data.split(' '); const [bMonth, bYear] = b.data.split(' '); // 优先按年份升序比较 if (aYear !== bYear) { return parseInt(aYear) - parseInt(bYear); } // 同年份则按月份顺序比较 return monthMap[aMonth] - monthMap[bMonth]; }); // 合并得到最终数组 const newDataset = [firstItem, ...restItems];
代码说明
- 拆分数组:单独保留第一个元素,避免排序操作影响其位置;
- 月份映射:将月份缩写转为数字,解决字符串无法直接按自然月份顺序比较的问题;
- 排序逻辑:
- 先对比年份,转为整数后做升序比较,小年份在前;
- 年份相同时,通过映射表的数值对比实现月份的自然顺序排列;
- 合并结果:将保留的首元素和排序后的剩余元素合并,得到符合需求的数组。
内容的提问来源于stack exchange,提问作者grabrep gg
相关产品推荐
相关产品推荐

