在JavaScript中构建mergesort时的无限循环
Posted
tags:
篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了在JavaScript中构建mergesort时的无限循环相关的知识,希望对你有一定的参考价值。
我正在尝试构建一个猴子修补版本的mergeSort
,但我每次都遇到错误。我已经运行了几次调试器,看起来一切都正常排序,直到最后一步我跳转到loader.js文件中的一行。
任何人都可以帮我看一下吗?提前致谢!
Array.prototype.mergeSort = function(callback) {
if (this.length <= 1) return this;
if (!callback) {
callback = function(x, y) {
if (x > y) return -1;
else if (x < y) return 1;
else return 0;
};
}
const mid = Math.floor(this.length / 2);
const sortedLeft = this.slice(0, mid).mergeSort(callback);
const sortedRight = this.slice(mid).mergeSort(callback);
return sortedLeft.merge(sortedRight, callback);
};
Array.prototype.merge = function(arr, callback) {
let merged = [];
while (this.length > 0 || arr.length > 0) {
if (callback(this[0], arr[0]) < 0) {
merged.push(arr.shift());
break;
} else if (callback(this[0], arr[0]) >= 0) {
merged.push(this.shift());
break;
}
}
merged = merged.concat(this);
merged = merged.concat(arr);
return merged;
};
答案
当任一列表为空时,合并循环应该停止:而不是while (this.length > 0 || arr.length > 0)
你应该写:
while (this.length > 0 && arr.length > 0)
此外,你不应该在每个商店进入break
数组后从循环中merge
,并且两次比较元素是多余的。
这是一个更正版本:
Array.prototype.merge = function(arr, callback) {
let merged = [];
while (this.length > 0 && arr.length > 0) {
if (callback(this[0], arr[0]) < 0) {
merged.push(arr.shift());
} else {
merged.push(this.shift());
}
}
merged = merged.concat(this);
return merged.concat(arr);
};
但请注意,您的merge
方法按降序对数组进行排序,默认的callback
函数也按降序对元素进行比较,导致数组按重合顺序递增排序。您可能希望简化此操作并接受null
中的merge
回调函数。
这是一个更通用的版本:
Array.prototype.mergeSort = function(callback) {
if (this.length <= 1)
return this;
const mid = this.length >> 1;
const sortedLeft = this.slice(0, mid).mergeSort(callback);
const sortedRight = this.slice(mid).mergeSort(callback);
return sortedLeft.merge(sortedRight, callback);
};
Array.prototype.merge = function(arr, callback) {
let merged = [];
if (callback) {
while (this.length > 0 && arr.length > 0) {
if (callback(this[0], arr[0]) <= 0) {
merged.push(this.shift());
} else {
merged.push(arr.shift());
}
}
} else {
while (this.length > 0 && arr.length > 0) {
if (this[0] <= arr[0]) {
merged.push(this.shift());
} else {
merged.push(arr.shift());
}
}
}
return merged.concat(this).concat(arr);
};
以上是关于在JavaScript中构建mergesort时的无限循环的主要内容,如果未能解决你的问题,请参考以下文章
为啥在 MergeSort 中使用 InsertionSort 而不是 Merge 平均更快?
Javascript 速记 - '||' 是啥意思运算符在作业中使用时的意思? [复制]