91超碰碰碰碰久久久久久综合_超碰av人澡人澡人澡人澡人掠_国产黄大片在线观看画质优化_txt小说免费全本

溫馨提示×

溫馨提示×

您好,登錄后才能下訂單哦!

密碼登錄×
登錄注冊×
其他方式登錄
點擊 登錄注冊 即表示同意《億速云用戶服務條款》

快速排序的分析與實現

發布時間:2020-09-17 00:44:29 來源:網絡 閱讀:256 作者:清幽寧 欄目:編程語言

快速排序是一種使用性非常強的排序算法,雖然它最壞的情況下時間復雜度O(N^2),但平均時間復雜度是O(N*logN),并在內存的使用、程序算法的復雜性上表現優秀,尤其是對快速排序進行隨機化的可能,快速排序是最使用的一種算法之一。

  算法思想:

    1.創建一個臨時變量,把數組中最右邊的值保存起來,最右邊就形成一個坑。

    2.然后找左邊大于臨時變量的那個值放到坑里,這樣左邊會形成新的坑。

    3.在找右邊小于臨時變量的那個值放到新的坑里,就這樣一直找。

    4.知道找完,最后把臨時變量放到最后形成的那個坑里。

    5.在把這個數組分成兩個子序列,特點:左邊的子序列中的數小于等于右邊的子序列中的數。

    6.在通過遞歸調用,來排序子序列。

    5.知道子序列排完,然后合并。(由于子序列是就地序列,所以合并不需要操作,排序已經完成)

實現代碼:

Sort.h中

int SingleSort(int *a, int left, int right)
{
    assert(a);
  int tmp = a[right];//臨時變量保存值
        while (left < right)
     {
           //找左邊大于等于tmp的數
              while (left < right&&tmp >= a[left])
          {
                   left++;
             }
           if (left < right)
                {
                   a[right--] = a[left];//把值給右邊,然后--
           }
           //找右邊小于等于tmp的值
              while (left < right&&tmp <= a[right])
         {
                   right--;
            }
           if (left < right)
                {
                   a[left++] = a[right];//把值給左邊,然后++
           }
   }
   a[left] = tmp;
      return left;
}
void QuickSort(int *arr, int left, int right)
{
     if (arr == NULL)
    {
           return;
     }
   if (left < right)
        {
           //遞歸調用
              int div = SingleSort(arr, left, right);
             QuickSort(arr, left, div - 1);
              QuickSort(arr, div + 1, right);
     }
}
//打印函數
void Print(int *arr, int size)
{
     for (int i = 0; i < size; i++)
   {
           cout << arr[i] << " ";
  }
   cout << endl;
}

test.cpp中

#include<iostream>
using namespace std;
#include "Sort.h"

void Test()
{
  int arr[] = { 3, 9, 7, 6, 1, 2, 4, 8, 0, 5 };
       QuickSort(arr, 0,sizeof(arr) / sizeof(arr[0])-1);
   Print(arr, sizeof(arr) / sizeof(arr[0]));
}
int main()
{
   Test();
     system("pause");
    return 0;
}

  我曾經看過看過一篇博客,快速排序對小范圍數字排序會花費很多時間,通過我查詢資料得知,數字總量小于13,用直接插入排序表較好,超過這個數字用快速排序。然后我就把代碼改了一下.

//直接插入排序
void InsertSort(int *a, int size)
{
        int end;
    int tmp;
    for (int i = 0; i < size - 1; i++)
       {
           end = i;
            tmp = a[end + 1];
           while (end >= 0 && tmp<a[end])
                {
                   a[end + 1] = a[end];
                        end--;
              }
           a[end + 1] = tmp;
   }
}
void QuickSort(int *arr, int left, int right)
{
        if (arr == NULL)
    {
           return;
     }
   if (right < 13)
  {
           InsertSort(arr, right + 1);
 }
   else
        {
           if (left < right)
                {
                   //遞歸調用
                      int div = SingleSort(arr, left, right);
                     QuickSort(arr, left, div - 1);
                      QuickSort(arr, div + 1, right);
             }
   }
}

   上面的代碼還不夠好,如果快速排序是,你的運氣比較差,每次取出的數都是最大或者最小,這樣的話他就會變成最壞一種情況,時間復雜度為O(N^2),為了避免這種情況,我想到一種辦法,三數取中法,

它是什么意思?

   三個數分別為最左邊,最右邊,中間這三個數,取得話,就取既不是最大也不是最小的這個數,這樣就能避免上面那種情況。

//三數取中
int Mid(int *a, int left, int right)
{
        int mid = left - (left - right);
    if (a[left] < a[right])
  {
           if (a[left]>a[mid])
              {
                   return a[left];
             }
           else if (a[right] < a[mid])
              {
                   return a[right];
            }
           else
                {
                   return a[mid];
              }
   }
   else
        {
           if (a[right] > a[mid])
           {
                   return a[right];
            }
           else if (a[left] < a[mid])
               {
                   return a[left];
             }
           else
                {
                   return a[mid];
              }
   }
}
int SingleSort(int *a, int left, int right)
{
  assert(a);
  int tmp = Mid(a,left,right);//臨時變量保存值,三數取中
  while (left < right)
     {
           //找左邊大于等于tmp的數
              while (left < right&&tmp >= a[left])
          {
                   left++;
             }
           if (left < right)
                {
                   a[right--] = a[left];//把值給右邊,然后--
           }
           //找右邊小于等于tmp的值
              while (left < right&&tmp <= a[right])
         {
                   right--;
            }
           if (left < right)
                {
                   a[left++] = a[right];//把值給左邊,然后++
           }
   }
   a[left] = tmp;
      return left;
}

這樣就比較完善了,如果我不想用遞歸,該這么辦那?然后我就想到了借助棧來實現。

void QuickSort(int *arr, int left, int right)
{
   stack<int> s;
 s.push(left);//壓棧數組的左下標
     s.push(right);//壓棧數組的有下標
    while (!s.empty())
  {
           int tmpRight = s.top();
             s.pop();
            int tmpLeft = s.top();
              s.pop();
            //把數組排序成左區間的數小于等于有區間的數
              int div = SingleSort(arr, tmpLeft, tmpRight);
               //壓棧左區間的左右兩個數的下標
            if (tmpLeft < div - 1)
           {
                   s.push(tmpLeft);
                    s.push(div - 1);
            }
           //壓棧右區間的左右兩個數的下標
             if (div + 1 < tmpRight)
         {
                   s.push(div + 1);
                    s.push(tmpRight);
           }
   }
}

  寫到這里,我有想到了另一種實現SingleSort()函數的方法,感覺比上面的更簡單,不過理解起來比較抽象。

    思想:

     1.定義一個cur為a[0]位置的下標

     2.在定義一個prev為a[0]的前一個位置。

     3.當a[0]位置的值小于最右邊的值。

     4.++prev,然后交換prev和cur對應的值。

     5.如果小于最右邊的值,++prev,prev和最右邊值交換。

     6.一直進行下去,就會讓左邊的值小于等于右邊的值。

int SingleSort(int *arr, int left, int right)
{
       int cur = left;
     int prev = cur - 1;
 int key = Mid(arr, left, right);
    swap(arr[right], key);//把key的值放到最右邊
 while (cur < right)
      {
           //++prev != cur防止自己和自己交換
            if (arr[cur]<=arr[right]&&++prev != cur)
         {
                   swap(arr[prev], arr[cur]);
          }
           cur++;
      }
   swap(arr[++prev], arr[right]);
      return prev;
}


向AI問一下細節

免責聲明:本站發布的內容(圖片、視頻和文字)以原創、轉載和分享為主,文章觀點不代表本網站立場,如果涉及侵權請聯系站長郵箱:is@yisu.com進行舉報,并提供相關證據,一經查實,將立刻刪除涉嫌侵權內容。

AI

昌吉市| 德保县| 丰原市| 秦安县| 富裕县| 梨树县| 二连浩特市| 遂川县| 延川县| 武义县| 安龙县| 明星| 娄底市| 汤阴县| 徐水县| 高邮市| 定远县| 都江堰市| 盐城市| 辰溪县| 福安市| 南靖县| 嘉兴市| 张家港市| 郧西县| 无棣县| 含山县| 永登县| 邢台县| 师宗县| 肇州县| 紫云| 商丘市| 凉山| 嘉祥县| 迭部县| 台山市| 景宁| 宁陵县| 璧山县| 东城区|