排序篇-内部排序-交换排序

247 阅读2分钟

冒泡排序

冒泡排序是一种稳定的排序。

代码

void bubble(int *a, int n){
	int tmp;
	for(int i = 0; i < n; i ++){
    	for(int j = i + 1; j < n; j ++){
        	if(a[i] > a[j]){
            	tmp = a[i];
                a[i] = a[j];
                a[j] = tmp;
            }
         }
	}
}

优化版

优化的目的在于减少不必要的比较

void bubble(int *a, int n){
	int flag = 0, tmp;
	for(int i = 0; i < n - 1; i ++){
    	flag = 0;
    	for(j = n - 1; j > i; j --){
        	if(a[j - 1] > a[j]){
            	tmp = a[j - 1];
                a[j-1] = a[j];
                a[j] = tmp;
                flag = 1;
            }
        }
        if(flag == 0){
        	return;
        }
    }
}

快速排序

严奶奶认为快速排序是性能比较优秀的内部排序

  • 时间复杂度最好O(nlog(n)),最坏O(n^2)
  • 最好O(log(n)),最坏O(n)
  • 稳定的性,不稳定
  • 基本思想 分治思想:在待排序表中任选一个元素pivot作为枢轴,通过一趟排序将待排序表划分成独立的两部分,使其左半部分的元素都小于pivot,右半部分的元素都大于等于pivot,则pivot已就位,这个过程称为一趟快速排序。然后分别递归的对两个子表重复上述过程,直到每部分内只有一个元素为止,即所有元素到达最终位置上。

代码实现

int partition(int *a, int low, int high){
	int pivot = a[low];
 	while(low <	 high){
    	while(low < high && a[high] >= pivot) high --;
        a[low] = a[high];
        while(low < high && a[low] < pivot) low ++;
        a[high] = a[low];
    }
 	a[low]  = pivot;
    return low;
}

void quickSort(int *a, int low, int high){
	if(low >= high) return;
	int pivot;
    pivot = partition(a, low, high);
    quickSort(a, low, pivot - 1);
    quickSort(a, pivot + 1, high);
}

快速查找数组的第k大元素

在快速排序中,经过一趟排序后,pivot元素将就位,将pivot元素所在位置pos与k比较,如果pos等于k,则pivot就是第k大元素,如果pos比k小,则说明第k大元素在分区的右边,否则在左边。理想情况下,算法的查找效率与二分查找相似,算法的时间复杂度为O(log(n));

代码实现

int partition(int *a, int low, int high){
	int pivot = a[low];
   	while(low < high){
    	while(low < high && a[high] >= pivot) high --;
        a[low] = a[high];
        while(low < high && a[low] < pivot) low ++;
        a[high] = a[low];
    }
    a[low] = pivot;
    return low;
}
int findKTh(int *a, int low, int high, int k){
	if(k > n) return -1;
	int pivot = partition(a, low, high);
    int pos = pivot + 1;
    if(pos == k){
    	return a[pivot];
    }else if(pos > k){ //在pivot的左边
    	return findKTh(a, low, pivot - 1, k); 
    }else{//在pivot的右边
    	return findKTh(a, pivot + 1, high, k);
    }
}