js-基础排序实现(冒泡排序,快速排序,选择排序,插入排序,希尔排序,归并排序,堆排序)

冒泡排序

:两个指针循环,遇到不合适就交换,直到将符合要求的浮到边界

function bubbleSort(list){
	for(let i=0;i<list.length;i++){
		for(let j=0;j<list.length-i-1;j++){
			if(list[j]>list[j+1]){
				let tmp=list[j]
				list[j]=list[j+1]
				list[j+1]=tmp
			}
		}
	}
}

快速排序

:重点在于如何实现partition,一般取左边做piovt,第一种方法是从左往右找,比标志小的就交换到左边排成一排。第二种方法是,左右轮流判断,遇到符合要求但在对面的就交换过来,最后把中间取成记录的值就行。

function swap(list , i ,j){
	let tmp=list[i]
	list[i]=list[j]
	list[j]=tmp
}

function partition0(list, left, right) {
  let index = left + 1;
  let piovt = list[left];
  for (let i = left + 1; i <= right; i++) {
  //上方的<=尤其容易不小心写成<
	if (list[i] < piovt) {
	  swap(list, i, index++);
	}
  }
  swap(list, index - 1, left);
  return index - 1;
}

function partition(list,left,right){
	let pivot=list[left]
	while(left<right){
		while(left<right&&list[right]>pivot){
			right--
		}
		list[left]=list[right]
		while(left<right&&list[left]<=pivot){
			left++
		}
		list[right]=list[left]
	}
	list[left]=pivot
	return left
}
function quickSort(list,left,right){
	if(left<right){
		let pivot=partition(list,left,right)
		quickSort(list,left,pivot-1)
		quickSort(list,pivot+1,right)
	}
}

选择排序

function selectSort(list){
	for(let i=0;i<list.length;i++){
		let min=i
		for(let j=i+1;j<list.length;j++){
			if(list[min]>list[j]){
				min=j
			}
		}
		let tmp=list[i]
		list[i]=list[min]
		list[min]=tmp
	}
}

插入排序

function insertSort(list){
	for(let i=1;i<list.length;i++){
		let key=list[i]
		let j
		for(j=i-1;(j>=0)&&(key>list[j]);j--){
			list[j+1]=list[j]
		}
		list[j+1]=key
	}
}

希尔排序

function shellSort(list){
	let gap=1
	while(gap<list.length/3){
		gap=gap*3+1
	}
	for(gap;gap>0;gap=Math.trunc(gap/3)){
		for(let i=gap;i<list.length;i+=1){
			let key=list[i],j
			for(j=i-gap;list[j]>list[j+gap];j-=gap){
				list[j+gap]=list[j]
			}
			list[j+gap]=key
		}
	}
}

归并排序

function merge(left,right){
	let res=[]
	while(left.length&&right.length){
		if(left[0]<right[0]){
			res.push(left.shift())
		}else{
			res.push(right.shift())
		}
	}
	while(left.length){
		res.push(left.shift())
	}
	while(right.length){
		res.push(right.shift())
	}
	return res
}
function mergeSort(list){
	if(list.length<2){
		return list
	}
	let mid=Math.trunc(list.length/2)
	return merge(mergeSort(list.slice(0,mid)),mergeSort(list.slice(mid)))
}

堆排序

//完全二叉树,第一个非叶子节点index=n/2-1
//父节点index=(n-1)/2
//子节点index=n2+1 n2+2

function heapfy(list,i,len){
	let left=i*2+1
	let right=i*2+2
	let largest=i
	if(left<len&&list[left]>list[largest]){
		largest=left
	}
	if(right<len&&list[right]>list[largest]){
		largest=right
	}
	if(i!=largest){
		swap(list,largest,i)
		heapfy(list,largest,len)
	}
}
function heapSort(list){
	for(let i=Math.trunc((list.length-1)/2);i>=0;i--){
		heapfy(list,i,list.length)
	}
	for(let i=list.length-1;i>0;i--){
		swap(list,0,i)
		heapfy(list,0,i)
	}
	return list
}

复杂度

image

参考

排序算法及其时间复杂度

十大经典排序算法

posted @ 2022-10-29 16:20  badpear  阅读(49)  评论(0)    收藏  举报