快速排序学习

介绍

  • 快速排序可能是应用最广泛的排序算法了,快速排序流行的原因是它实现简单,适用于各种不同的输入数据且在一般应用中比其他算法都要快的多。
  • 一般的情况下时间复杂度为 O(N*ln(n))
  • 但相对来说,快速排序排序速度较快,但是不稳定,最坏的情况下,时间复杂度为O(N^2)

基本算法

  • 快速排序是一种分治的排序算法,将一个数组分成两个子数组,将两部分独立地进行排序。
  • 快速排序和归并排序是互补的:
    • a、 归并排序将数组分成两个子数组分别排序,并将有序的子数组归并以将数组排序,而快速排序将数组排序的方式则是当两个子数组都有序时整个数组也就自然有序了,
    • b、 归并排序递归调用发生在处理整个数组之前;快速排序递归调用发生在处理整个数组之后。
    • c、 在归并排序中,一个数组被切分为两半;在快速排序中切分的位置取决于数组的内容。
      在这里插入图片描述

策略是

  • a、 随意地取a[lo]作为切分元素。
  • b、 然后从数组的左端开始向右扫描直到找到一个大于等于它的元素,
  • c、 再从数组的右端开始向左扫描直到找到一个小于等于它的元素,
  • d、 交换这两个元素的位置。
  • e、 如此继续。
  • f、 当两指针相遇时,只需将切分元素a[lo]和左子树的最右侧元素(a[j])交换然后返回j即可。

Java代码:

import java.util.Arrays;

public class Main {
    public static void main(String[] args){
        int[] arr={5,1,7,8,3,2,9,4};
        System.out.println("原数组:"+Arrays.toString(arr));
        quitSort(arr);
        System.out.println("排序之后的数组:"+Arrays.toString(arr));

    }


    // 快排包装
    public static void quitSort(int[] arr){
        quitSort(arr,0,arr.length-1);
    }
    //快速排序,可以将arr数组,将left~right进行排序
    public static void quitSort(int arr[],int left,int right){
        //终止条件
        if(left>=right){
            return;
        }
        int mid = partition(arr,left,right);
        quitSort(arr,0,mid-1);
        quitSort(arr,mid+1,right);

    }
    public static int partition(int[] arr,int low,int high){
        while(low<high){
            while (low<high && arr[low]<arr[high]){
                high--;
            }
            if(low<high){
                int temp = arr[low];
                arr[low] = arr[high];
                arr[high] = temp;
                low++;
            }
            while(low<high && arr[low]<=arr[high]){
                low++;
            }
            if(low<high){
                int temp = arr[low];
                arr[low] = arr[high];
                arr[high] = temp;
                high--;
            }
        }
        return low;
    }
}

在这里插入图片描述

#include <iostream>
using std::cin;
using std::endl;
using std::cout;

int swap(int* arr,int i,int j){
    int t = arr[i];
    arr[i] = arr[j];
    arr[j] = t;
}

int partition(int *arr,int low,int high){
    while(low<high){
        //右边的元素大于左边的元素
        while(low<high && arr[low]<arr[high]){
            //箭头左移
            high--;
        }
        if (low<high)
        {
            swap(arr,low,high);
            //左边的元素右移
            low++;
        }
        while (low<high && arr[low]<=arr[high])
        {
            low++;
        }
        if(low<high){
            swap(arr,low,high);
            high--;
        }
        
    }
    return low;
}

void quitSort1(int* arr,int left,int right){
    //用递归的方法实现快排
    //首先是递归的终止条件
    if(left>=right){
        return;
    }
    int mid = partition(arr,left,right);
    quitSort1(arr,0,mid-1);
    quitSort1(arr,mid+1,right);
}

//快速排序包装
void quitSort(int* arr){
    quitSort1(arr,0,8);
}


int main(){
    int arr[]={5,1,7,8,9,2,0,10,3,10};
    cout<<"排序之前的数组:";
    for (int i = 0; i < sizeof(arr)/sizeof(arr[0]); i++)
    {
        cout<<arr[i]<<" ";
    }
    cout<< endl;
    quitSort(arr);
    cout<<"排序之后的数组:";
    for (int i = 0; i < sizeof(arr)/sizeof(arr[0]); i++)
    {
        cout<<arr[i]<<" ";
    }
    return 0;
}

在这里插入图片描述

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值