quicksort快排

1.从待排的数里随便取分界点x,常用两边或中间

2.考虑两个指针i,j分居数两侧,如果指针i指向的数左小于x或右边的j大于x,则向中间走一格。如果i大于x或者j小于x,则停下,等两边停下,交换数。从而保证在x的左边都小于等于x,右边同理

3.由此,一串数通过x划分为左右两串数,对每一串数递归处理即可

代码实现

void quick_sort(int q[],int left,int right){
    if(left==right)return ;
    int i=left-1,j=right+1;
    int s=q[(left+right)/2];
    while(i<j)//结束循环意味着i>=j,此时代表完成{
        do i++;while(q[i]<s);
        do j--;while(q[j]>s);
        if(i<j){
        int temp=q[j];
        q[j]=q[i];
        q[i]=temp;
        }
    }
    quick_sort(q,left,j);
    quick_sort(q,j+1,right);
}

需要注意,

1.s应该是q[(left+right)/2]这个固定值,而不是left+right)/2这个索引,因为虽然s不变,但后面while交换时可能打乱变动q[s]值。

2.建议递归的(q,left,j)不写成(q,left,j-1),因为当排序只有两个,左边指针一来就停止时,右边会到最左边,造成左边的数分串是零,右边跟原来一模一样,造成无限递归。同理,s=q[r]时,尽量避开(q,left,j)

即s=q[left]或left+right/2----j,j+1;s=q[right]或者left+right+1/2----i-1,i。

3.为什么是j,j+1而不是j-1,j?

考虑结束时仅有i=j(指向同一个地点)和----ji-----i在j后面一个,显然划分数串的就是ji中间的缝,对应索引j,j+1或者i-1,i(这里选择ij需要注意2的问题,如果是取中间还是j,毕竟c是向小取整)

posted @ 2025-07-26 09:43  hardestnut  阅读(11)  评论(0)    收藏  举报