)我有一个JS应用程序需要做一个复杂的大型数组,然后显示它。使用内置的array.sort(cb)
方法可能需要1秒钟的时间才能处理我的数据。这足以让我的用户界面变得很笨拙。如何批量排序JS数组(
由于用户界面的高度足以显示屏幕上的排序数组的子集,其余部分位于滚动或分页之下,因此我有一个想法。如果我制作了一个通过大型数组的算法,并且快速按照前N个项目完全排序的方式进行排序,但是数组中的其余项不完全排序。每次运行我的算法时,它都会从上到下排列更多的数组。
因此,我可以将我的处理分解为块并拥有流畅的UI。在头几秒钟数组不会被完美排序,但缺陷会在滚动下方,所以他们不会被注意到。
我天真的解决方案是编写我自己的“选择排序”,能够在N次匹配后中断并稍后恢复,但“选择排序”是一个非常糟糕的算法。更快的算法(从我的理解)必须完成,以确保前N个项目是稳定的。
有没有人知道现有的解决方案呢?我疯了吗?有什么建议么?
UPDATE
回吐@moreON提出这个想法,我写道,捞出一旦它具有精度要求的自定义快速排序。这种数据的本地排序需要1秒。常规的QuickSort花费了大约250毫秒,这已经非常好了。在排序前100个项目后排序的QuickSort花了10毫秒,这要好得多。然后我可以再花250ms来完成排序,但这并不重要,因为用户已经在查看数据。这将用户的经验延迟从1秒减少到10毫秒,这非常好。
//Init 1 million random integers into array
var arr1 = [];
var arr2 = [];
for(var i=0;i<1800000;i++) {
var num = Math.floor(Math.random() * 1000000);
arr1.push(num);
arr2.push(num);
}
console.log(arr1);
//native sort
console.time("native sort");
arr1.sort(function(a,b) { return a-b; });
console.timeEnd("native sort"); //1sec
console.log(arr1);
//quicksort sort Ref: https://www.nczonline.net/blog/2012/11/27/computer-science-in-javascript-quicksort/
function swap(arr, a, b) {
var temp = arr[a];
arr[a] = arr[b];
arr[b] = temp;
}
function cmp(a,b) {
return (a<b);
}
function partition(items, left, right) {
var pivot = items[Math.floor((right + left)/2)];
var i = left;
var j = right;
while (i <= j) {
while (cmp(items[i],pivot)) i++;
while (cmp(pivot,items[j])) j--;
if (i <= j) {
swap(items, i, j);
i++;
j--;
}
}
return i;
}
function quickSort(items, left, right, max) {
if(max && left-1 > max) return items; //bail out early if we have enough
if (items.length > 1) {
var index = partition(items, left, right);
if (left < index - 1) quickSort(items, left, index - 1, max);
if (index < right) quickSort(items, index, right, max);
}
return items;
}
//sort first 100
console.time("partial Quicksort");
arr2 = quickSort(arr2,0,arr2.length-1,100);
console.timeEnd("partial Quicksort"); //10ms
console.log(arr2);
//sort remainder
console.time("finishing Quicksort");
arr2 = quickSort(arr2,100,arr2.length-1); //250ms
console.timeEnd("finishing Quicksort");
console.log(arr2);
请加你尝试。 –
如果您的数据集没有完全排序,是不是有可能第一个项目不应该是您向用户展示的数组中的第一个项目? – Bryce
对不起,但我认为你可能有点疯狂,我想纠正,但我不认为你可以保证没有访问所有项目的部分排序。至多你可以保证**你已经排序的项目**,它们是完全分类的。在至少访问过一次之前,您无法与剩余的项目交谈。 “选择排序”将工作,但它的指数算法,疯狂缓慢。我非常确定'array.sort'是一种快速排序,对于大多数数据分布来说,你可能无法做得更好。 – Jim