【发布时间】:2020-06-02 21:34:22
【问题描述】:
我正在尝试了解 JavaScript 合并排序功能的工作原理。我很难理解递归函数是如何工作的。这是代码:
const mergeSort = array => {
if (array.length < 2) {
//function stop here
return array
}
const middle = Math.floor(array.length / 2);
const leftSide = array.slice(0, middle);
const rightSide = array.slice(middle, array.length);
return merge(mergeSort(leftSide), mergeSort(rightSide))
};
const merge = (left, right) => {
const result = [];
while (left.length && right.length) {
if (left[0] <= right[0]) {
result.push(left.shift());
} else {
result.push(right.shift);
}
}
while(left.length) result.push(left.shift());
while(right.length) result.push(right.shift());
return result;
}
mergeSort([5,3,8,10,4,1])
【问题讨论】:
-
请注意,所有值要么是当前函数调用的本地值,要么是传递给它的参数。所以在
[5]和[3, 8]排序之后,return merge...行调用merge和[5]和[3, 8],返回[3, 5, 8]。类似的事情发生在右半部分:[10]被返回,[4, 1]被排序到[1, 4],然后[10]和[1, 4]被合并到[1, 4, 10]。最后[3, 5, 8]和[1, 4, 10]合并成[1, 3, 4, 5, 8, 10]。每个递归调用都会保留自己的局部变量副本。 -
把它写在纸上:你从
[5, 3, 8, 10, 4, 1]开始,它在mergeSort中被分成两个数组。这两个数组都(递归地)再次传递给mergeSort,其中[5, 3, 8]变为[5]和[3, 8]。对于[5],我们完成了,它按原样返回。对于[3,8],我们再次递归,它们最终返回为[3]和[8]。那些得到merged:在合并步骤中会发生什么?写出来:如果你想了解任何算法,这是一个重要的练习。 -
但是首先像merge(3, 8)那样调用merge,然后执行但函数本身不能保留这些值,然后用5再次执行,但我不知道5是如何传递的merge([3,8,5]) 因为 mergeSort 只返回一个值...
-
嘿,迈克,合并函数或合并中的拆分处理是否仅使用单个参数调用?
-
@shaunaa - 使用两个参数调用合并,每个参数都是一个数组,合并返回一个合并数组。这是实现归并排序的一种非常低效的方式。最好一次性分配第二个数组,然后在两个数组之间来回合并,将数组和索引作为参数传递。
标签: javascript arrays sorting recursion mergesort