如何排序任意维度的复杂数值型多维JavaScript数组?
任意维度嵌套数组的排序实现
需求说明
需要排序的目标数组:
const array = [ [18, [18, 16], 16], 15, [18, 19, 51], [[18, 16], 15, [14, 13]], [10, 9, 20], 99, 49, [11, [22, 10], [[10, 9], 11, 9, [1, 2]], 100, 72], [[11], [[19, 14], [77, 18]]] ];
排序规则:
- 单个元素排在最前,之后依次是一维数组、二维数组、三维数组……按维度从小到大排列
- 所有数组内部的元素也需要遵循相同规则排序
预期结果:
[ 15, 49, 99, [18, 19, 51], [9, 10, 20], [16, 18, [16, 18]], [15, [16, 18], [13, 14]], [11, 72, 100, [10, 22], [9, 11, [9, 10], [1, 2]]], [[11], [[14, 19], [18, 77]]] ]
当前实现的问题
现有代码通过sort_array1到sort_array4分别处理不同维度的数组,仅支持到四维结构,无法适配任意深度的嵌套数组,扩展性差。
优化实现:递归处理任意维度
通过递归方式,无需针对每个维度单独写函数,自动适配所有嵌套深度:
const array = [ [18, [18, 16], 16], 15, [18, 19, 51], [[18, 16], 15, [14, 13]], [10, 9, 20], 99, 49, [11, [22, 10], [[10, 9], 11, 9, [1, 2]], 100, 72], [[11], [[19, 14], [77, 18]]] ]; // 计算元素的嵌套深度 function getArrayDepth(value) { return Array.isArray(value) ? 1 + Math.max(0, ...value.map(getArrayDepth)) : 0; } // 递归排序单个数组:先排序内部元素,再按深度分组排序 function sortNestedArray(arr) { // 先递归排序每个子元素 const processedElements = arr.map(item => { return Array.isArray(item) ? sortNestedArray(item) : item; }); // 按元素深度分组 const groups = {}; processedElements.forEach(item => { const depth = getArrayDepth(item); if (!groups[depth]) groups[depth] = []; groups[depth].push(item); }); // 对每个分组内的元素排序:单个元素按数值排序,数组按深度+内部值排序 Object.keys(groups).sort((a, b) => a - b).forEach(depth => { groups[depth].sort((x, y) => { if (!Array.isArray(x) && !Array.isArray(y)) { return x - y; } // 数组之间先比深度,深度相同则转成字符串比较(保证排序稳定) const xDepth = getArrayDepth(x); const yDepth = getArrayDepth(y); if (xDepth !== yDepth) return xDepth - yDepth; return JSON.stringify(x).localeCompare(JSON.stringify(y)); }); }); // 按深度从小到大合并所有分组 const result = []; Object.keys(groups).sort((a, b) => a - b).forEach(depth => { result.push(...groups[depth]); }); return result; } // 顶层排序:按元素深度分组,再分别排序后合并 function sequencedArray(arr) { // 先处理每个元素的内部排序 const processedItems = arr.map(item => { return Array.isArray(item) ? sortNestedArray(item) : item; }); // 按深度分组 const depthGroups = {}; processedItems.forEach(item => { const depth = getArrayDepth(item); if (!depthGroups[depth]) depthGroups[depth] = []; depthGroups[depth].push(item); }); // 每个分组内排序,然后按深度顺序合并 const sortedResult = []; Object.keys(depthGroups).sort((a, b) => a - b).forEach(depth => { const group = depthGroups[depth]; group.sort((x, y) => { if (!Array.isArray(x) && !Array.isArray(y)) { return x - y; } const xDepth = getArrayDepth(x); const yDepth = getArrayDepth(y); if (xDepth !== yDepth) return xDepth - yDepth; return JSON.stringify(x).localeCompare(JSON.stringify(y)); }); sortedResult.push(...group); }); return sortedResult; } const sortedArray = sequencedArray(array); console.log(sortedArray);
关键逻辑说明
getArrayDepth:递归计算元素的嵌套深度,单个元素深度为0,一维数组深度为1,以此类推。sortNestedArray:递归处理每个数组元素——先排序子元素,再将当前数组内的元素按深度分组,每组内排序后按深度顺序合并,保证内部元素符合排序规则。sequencedArray:处理顶层数组,按元素深度分组,每组内排序后按深度从小到大合并,实现整体排序规则。
这种方式无需针对固定维度写特定函数,无论数组嵌套多少层,都能自动处理。
内容的提问来源于stack exchange,提问作者Ankit Thummar
相关产品推荐
相关产品推荐

