加强版 一次循环中做两次比较
实现原理
1 在一次循环中比较出 最大 与 最小值, 分别放到数组的 两头
2 内层循环每次 起始索引加 1, 最大索引值减 1 , 缩小循环范围. 每循环一次结束, 数组待比较长度数减2.
3 记录元素位置交换的次数, 没有发生交换时, 退出外层循环, 完成排序.
最坏的情况, 也比 优化版本减少一半的循环次数.
var arr = [ 0, 0, 1, 2, 3, 4, 5, 6, 12, 22, 123, 333, 333, 444, 555, 666, 777, 888, 999];
function maoPao(arr) {
var arrLenght = arr.length;
var maxRange = arrLenght;
var minRange = 0;
var loopNum = Math.floor(arrLenght / 2);
function exchange(arr, n1, n2) {
if(arr[n1] > arr[n2]){
[arr[n1], arr[n2]] = [arr[n2], arr[n1]];
exchangeCount += 1;
}
}
// 辅助计数
var countAll = 0;
var exchangeAll = 0;
while (loopNum){
loopNum--;
//元素交换计数
var exchangeCount = 0;
for(let n=minRange; n < maxRange; n++){
exchange(arr, n+1, n);
exchange(arr, n, minRange);
countAll += 1;
}
if(exchangeCount == 0) break
exchangeAll += exchangeCount;
minRange++, maxRange--;
}
console.log('exchangeAll: ' + exchangeAll);
console.log('forLoop: ' + countAll);
return arr;
}
console.log(maoPao(arr));
输出
exchangeAll: 163
forLoop: 99
[ 999, 888, 777, 666, 555, 444, 333, 333, 123, 22, 12, 6, 5, 4, 3, 2, 1, 0, 0 ]
感觉代码上还可以优化, 我在这里只打算讲明白思路. js 语言本身还在熟练中...