zoukankan      html  css  js  c++  java
  • 785. 快速排序

    题目描述

    给定你一个长度为n的整数数列。

    请你使用快速排序对这个数列按照从小到大进行排序。

    并将排好序的数列按顺序输出。

    输入格式

    输入共两行,第一行包含整数 n。

    第二行包含 n 个整数(所有整数均在1~109

    范围内),表示整个数列。

    输出格式

    输出共一行,包含 n 个整数,表示排好序的数列。

    数据范围

    1 ≤ n ≤ 100000

    1n100000

    输入样例

    5

    3 1 2 4 5

    输出样例

    1 2 3 4 5

    思路

      快速排序时间复杂度O(N*logN),其思想是分治法,

      该方法的基本思想是:

      1.先从数列中取一个数k作为基准数(一般是数列的第一个数或中间那个数);

      2.分区过程,将比这个数大的数全放到它的右边,小于或等于它的数全放到它的左边.

      ①k为第一个数:设一个头指针i(此时i指向k),尾指针j,当i<j时,先从数列末端往前(j--)找到第一个小于k的数,将j指向的那个值放到i的位置,然后从i往后(i++)找到第一个大于k的数,将i指向的那个值放到j的位置. 直到最后i==j,k就放到这个位置;

      ②k为中间那个数:设一个头指针i,尾指针j,当i<j时,i向后移动直到i指向的数≥k,j向前移动直到j指向的数≤k,此时若i<j则将它们指向的两个数交换,然后继续重复这个步骤,直到i>=j;

      3.再对左右区间重复第二步,直到各区间只有一个数;

      一般我选择第一个数作为基准值,不过在这里超时了,代码如下——

     1 #include <iostream>
     2 #include <cstdio>
     3 #include <cstdlib>
     4 using namespace std;
     5 int q[100005];
     6 
     7 void quickSort(int l, int r) {
     8     if(l>=r) return;
     9     int i=l, j=r, k=q[l];
    10     while(i<j) {
    11         while(i<j && q[j]>=k) j--;
    12         q[i]=q[j];
    13         while(i<j && q[i]<=k) i++;
    14         q[j]=q[i];
    15     }
    16     q[i]=k;
    17     quickSort(l, i-1);
    18     quickSort(i+1, r);
    19 }
    20 
    21 int main() {
    22     int n;
    23     cin>>n;
    24     for(int i=0; i<n; i++) cin>>q[i];
    25     quickSort(0, n-1);
    26     for(int i=0; i<n; i++) cout<<q[i]<<' ';
    27 }

      然后改用中间数作为基准值了,但是因为不怎么用,所以出了bug,上个代码以告诫自己,避免错误重犯,要仔细审题——

     1 #include <iostream>
     2 #include <cstdio>
     3 #include <cstdlib>
     4 #include <algorithm>
     5 #include <cmath>
     6 using namespace std;
     7 
     8 int q[100005];
     9 
    10 void quickSort(int l, int r) {
    11     if(l>=r) return;
    12     int i=l,  j=r, k=q[l+r >> 1];
    13     while(1) {
    14         while (q[i]<k) i++;
    15         while (q[j]>k) j--;
    16         if(i>=j) break;
    17         swap(q[i], q[j]);
    18     }
    19     quickSort(l, j-1);
    20     quickSort(j+1, r);
    21 }
    22 
    23 int main() {
    24     int n;
    25     cin>>n;
    26     for(int i=0; i<n; i++) cin>>q[i];
    27     quickSort(0, n-1);
    28     for(int i=0; i<n; i++) cout<<q[i]<<' ';
    29     return 0;
    30 }

      分析错误数据可知,数列中存在相等的数,因为是用while,所以当q[i]和q[j]都为k时,i和j都不会更新,导致while陷入死循环,所以i要自增,j要自减;不过看了一下题解发现基本上都是用do...while...写的,所以说,平时不要只用一种写法,其他的写法也要熟悉,这样才能随机应变.

      以下是AC代码——

     1 #include <iostream>
     2 #include <cstdio>
     3 #include <cstdlib>
     4 #include <algorithm>
     5 #include <cmath>
     6 using namespace std;
     7 
     8 int q[100005];
     9 
    10 void quickSort(int l, int r) {
    11     if(l>=r) return;
    12     //do...while...
    13     int i=l-1,  j=r+1, k=q[l+r >> 1];
    14     while(i<j) {
    15         do i++; while(q[i]<k);
    16         do j--; while(q[j]>k);
    17         if(i<j) swap(q[i], q[j]);
    18     }
    19     //while...
    20 //    int i=l,  j=r, k=q[l+r >> 1];
    21 //    while(1) {
    22 //        while (q[i]<k) i++;
    23 //        while (q[j]>k) j--;
    24 //        if(i>=j) break;
    25 //        swap(q[i], q[j]);
    26 //        i++;
    27 //        j--;
    28 //    }
    29     quickSort(l, j);
    30     quickSort(j+1, r);
    31 }
    32 
    33 int main() {
    34     int n;
    35     cin>>n;
    36     for(int i=0; i<n; i++) cin>>q[i];
    37     quickSort(0, n-1);
    38     for(int i=0; i<n; i++) cout<<q[i]<<' ';
    39     return 0;
    40 }
  • 相关阅读:
    python加速包numba并行计算多线程
    idea Exception in thread "http-apr-8080-exec-2" java.lang.OutOfMemoryError: PermGen space
    centos6.5 导入matplotlib报错 No module named '_tkinter
    pythonTensorFlow实现yolov3训练自己的目标检测探测自定义数据集
    ajax post请求json数据在spring-controller解析
    python keras YOLOv3实现目标检测
    mybatis 插入语句name no find
    python调用百度语音识别接口实时识别
    idea ssm框架搭建
    OpenCVSSDpython目标探测对象检测
  • 原文地址:https://www.cnblogs.com/wwqzbl/p/13649152.html
Copyright © 2011-2022 走看看