【數據結構基礎】五大排序算法的C++實現(冒泡,選擇,插入,歸併,快排)

在這裏插入圖片描述

(目前只寫了這五個,後續的在更)

1. 冒泡排序:

1.1 算法流程:

  1. 比較相鄰的元素。如果第一個比第二個大,就交換它們兩個;
  2. 對每一對相鄰元素作同樣的工作,從開始第一對到結尾的最後一對,這樣在最後的元素應該會是最大的數;
  3. 針對所有的元素重複以上的步驟,除了最後一個;
  4. 重複步驟1~3,直到排序完成。

1.2 算法圖解:

在這裏插入圖片描述

1.3 代碼實現:

void BubbleSort(int a[], long size)
{
    // 冒泡排序
    for (long i = 0; i < size; i++)
    {
        bool flag = true;
        for (long j = 0; j < size - i - 1; j++)
        {
            if (a[j] > a[j + 1])
            {
                swap(a[j], a[j + 1]);
                flag = false;
            }
        }
        if (flag)
        {
            return;
        }
    }
}

2. 選擇排序:

2.1 算法流程:

  1. 初始狀態:無序區爲R[1…n],有序區爲空;
  2. 第i趟排序(i=1,2,3…n-1)開始時,當前有序區和無序區分別爲R[1…i-1]和R(i…n)。該趟排序從當前無序區中-選出關鍵字最小的記錄 R[k],將它與無序區的第1個記錄R交換,使R[1…i]和R[i+1…n)分別變爲記錄個數增加1個的新有序區和記錄個數減少1個的新無序區;
  3. n-1趟結束,數組有序化了。

2.2 算法圖解:

在這裏插入圖片描述

2.3 代碼實現:

void SelectSort(int a[], long size)
{
    // 選擇排序
    for (long i = 0; i < size; i++)
    {
        int minnum = a[i];
        long index = i;
        for (long j = i; j < size; j++)
        {
            if (a[j] <= minnum)
            {
                minnum = a[j];
                index = j;
            }
        }
        swap(a[index], a[i]);
    }
}

3. 插入排序:

3.1 算法流程:

  1. 從第一個元素開始,該元素可以認爲已經被排序;
  2. 取出下一個元素,在已經排序的元素序列中從後向前掃描;
  3. 如果該元素(已排序)大於新元素,將該元素移到下一位置;
  4. 重複步驟3,直到找到已排序的元素小於或者等於新元素的位置;
  5. 將新元素插入到該位置後;
  6. 重複步驟2~5。

3.2 算法圖解:

在這裏插入圖片描述

3.3 代碼實現:

void InsertSort(int a[], long size)
{
    // 插入排序
    for (long i = 1; i < size; i++)
    {
        int temp = a[i];
        long j;
        for (j = i - 1; j >= 0; j--)
        {
            if (a[j] > temp)
            {
                a[j + 1] = a[j];
            }
            else
            {
                break;
            }
        }
        a[j + 1] = temp;
    }
}

4. 歸併排序:

4.1 算法流程:

  1. 把長度爲n的輸入序列分成兩個長度爲n/2的子序列;
  2. 對這兩個子序列分別採用歸併排序;
  3. 將兩個排序好的子序列合併成一個最終的排序序列。

4.2 算法圖解:

在這裏插入圖片描述

4.3 代碼實現:

void MergeSort(int a[], long l, long r)
{
    // 歸併排序
    if (r - l < 2)
    {
        return;
    }
    long m = (l + r) / 2;
    MergeSort(a, l, m);
    MergeSort(a, m, r);
    Merge(a, l, m, r);
}

void Merge(int a[], long l, long m, long r)
{
    long ml = m - l;
    int *b = new int[ml];
    for (long i = 0; i < ml; i++)
        b[i] = a[l + i];
    long x = 0, y = m;
    for (long i = l; i < r;)
    {
        if ((b[x] <= a[y] && x < ml) || y >= r)
        {
            a[i++] = b[x++];
        }
        if ((a[y] < b[x] && y < r) || x >= ml)
        {
            a[i++] = a[y++];
        }
    }
    delete[] b;
}

5. 快速排序:

5.1 算法流程:

  1. 從數列中挑出一個元素,稱爲 “基準”(pivot);
  2. 重新排序數列,所有元素比基準值小的擺放在基準前面,所有元素比基準值大的擺在基準的後面(相同的數可以到任一邊)。在這個分區退出之後,該基準就處於數列的中間位置。這個稱爲分區(partition)操作;
  3. 遞歸地(recursive)把小於基準值元素的子數列和大於基準值元素的子數列排序。

5.2 算法圖解:

在這裏插入圖片描述

5.3 代碼實現:

void QuickSort(int a[], int l, int r)
{
    // 快速排序
    if (l < r)
    {
        int i = l, j = r, x = a[l];
        while (i < j)
        {
            while (i < j && a[j] >= x) // 從右向左找第一個小於x的數
            {
                j--;
            }
            if (i < j)
            {
                a[i++] = a[j];
            }
            while (i < j && a[i] < x) // 從左向右找第一個大於等於x的數
            {
                i++;
            }
            if (i < j)
            {
                a[j--] = a[i];
            }
        }
        a[i] = x;
        QuickSort(a, l, i - 1); // 遞歸調用
        QuickSort(a, i + 1, r);
    }
}

發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章