JavaScript受限环境下"dd MMMM"字符串数组去重及日期排序方案
对"dd MMMM"格式日期数组去重并按日期排序
问题背景
我有一个格式为dd MMMM的JavaScript字符串数组:
var myArray = ['13 October','13 November','13 May','13 August','13 November','13 February','13 May', '13 August','13 November','13 February','13 May','13 August','13 November','13 February','13 May', '13 August','13 November','13 February','13 May','13 August','13 November','14 November']
需要完成两个需求:
- 对数组去重
- 最终结果按日期自然顺序排列
最初尝试默认排序后去重,但字符串字典序排序会打乱日期顺序;临时方案是给日期拼接年份转成日期对象处理,但代码不够优雅。此外运行环境受限:不支持Set、indexOf、箭头函数、sortBy等方法。
解决方案
核心思路是通过月份映射表生成可排序的数值键,先去重再按数值键排序,完全兼容受限环境。
1. 定义月份顺序映射表
创建月份到数字的映射,用于确定每个月份的排序优先级:
var monthOrder = { "January": 1, "February": 2, "March": 3, "April": 4, "May": 5, "June": 6, "July": 7, "August": 8, "September": 9, "October": 10, "November": 11, "December": 12 };
2. 去重并生成排序键
遍历原数组,用对象记录已出现的日期(替代Set),同时为每个唯一日期生成排序键(月份数字*100 + 日期数字,确保小月份、小日期排在前面):
function processDates(arr) { var seen = {}; var uniqueDatesWithKey = []; for (var i = 0; i < arr.length; i++) { var dateStr = arr[i]; // 跳过已记录的日期 if (seen[dateStr]) continue; seen[dateStr] = true; // 拆分日期和月份 var parts = dateStr.split(' '); var day = parseInt(parts[0], 10); var month = parts[1]; // 生成排序键 var sortKey = monthOrder[month] * 100 + day; uniqueDatesWithKey.push({ date: dateStr, key: sortKey }); } return uniqueDatesWithKey; }
3. 基础排序并提取结果
用冒泡排序(兼容低版本环境)对带排序键的数组排序,最后提取日期字符串:
function sortDates(dateObjects) { var len = dateObjects.length; // 冒泡排序实现 for (var i = 0; i < len - 1; i++) { for (var j = 0; j < len - 1 - i; j++) { if (dateObjects[j].key > dateObjects[j+1].key) { // 交换元素位置 var temp = dateObjects[j]; dateObjects[j] = dateObjects[j+1]; dateObjects[j+1] = temp; } } } // 提取排序后的日期字符串 var sortedUnique = []; for (var k = 0; k < dateObjects.length; k++) { sortedUnique.push(dateObjects[k].date); } return sortedUnique; }
完整调用示例
var myArray = ['13 October','13 November','13 May','13 August','13 November','13 February','13 May', '13 August','13 November','13 February','13 May','13 August','13 November','13 February','13 May', '13 August','13 November','13 February','13 May','13 August','13 November','14 November']; var monthOrder = { "January": 1, "February": 2, "March": 3, "April": 4, "May": 5, "June": 6, "July": 7, "August": 8, "September": 9, "October": 10, "November": 11, "December": 12 }; // 执行流程 var processed = processDates(myArray); var result = sortDates(processed); console.log(result); // 输出:['13 February','13 May','13 August','13 October','13 November','14 November']
方案优势
- 避免日期解析的跨地区兼容性问题
- 用对象属性判断重复,完美替代受限方法
- 数值键排序比字符串排序更精准可靠
- 代码模块化,逻辑清晰易维护
内容的提问来源于stack exchange,提问作者hshah
相关产品推荐
相关产品推荐

