Unity中的快速排序算法&&二分查找

一、 快速排序

介紹:
  快速排序是由東尼·霍爾所發(fā)展的一種排序算法。在平均狀況下,排序 n 個項目要Ο(n log n)次比較。在最壞狀況下則需要Ο(n2)次比較,但這種狀況并不常見。事實上,快速排序通常明顯比其他Ο(n log n) 算法更快,因為它的內部循環(huán)(inner loop)可以在大部分的架構上很有效率地被實現出來,且在大部分真實世界的數據,可以決定設計的選擇,減少所需時間的二次方項之可能性。
步驟:
從數列中挑出一個元素,稱為 "基準"(pivot),
重新排序數列,所有元素比基準值小的擺放在基準前面,所有元素比基準值大的擺在基準的后面(相同的數可以到任一邊)。在這個分區(qū)退出之后,該基準就處于數列的中間位置。這個稱為分區(qū)(partition)操作。
遞歸地(recursive)把小于基準值元素的子數列和大于基準值元素的子數列排序。

using UnityEngine;
using System.Collections;

public class QuickSort : MonoBehaviour {
    //定義一個數組
    private int[] array = new int[] { 5, 9, 3, 1, 4, 7, 2 };

    void Awake()
    {
        //調用排序方法
        QuickSortArray(array, 0, array.Length - 1);
        //打印數組
        foreach (int item in array)
        {
            Debug.Log(item);
        }
    }
    /// <summary>
    /// 快速排序的方法
    /// </summary>
    /// <param name="array">數組</param>
    /// <param name="start">數組起始位置</param>
    /// <param name="end">數組終止位置</param>
    void QuickSortArray(int[] array, int start, int end)
    {
        //若數組中數小于等于0直接返回
        if (start >= end) return;
        //定義一個基準值
        int pivot = array[start];
        //定義2個索引指向數組的而開頭和結束
        int left = start;
        int right = end;
        //按照從小到大的排序,直到2數相遇結束排序
        while (left < right)
        {
            //第一輪比較
            //把所有l(wèi)eft右邊的數都和基準值比較,獲得最左邊數在排序后位于數組中的位置(索引)
            while (left < right  && array[right] >= pivot) 
            {
                right--;
            }
            //將該數放到數組中的該位置
            array[left] = array[right];
            //第二輪比較
            //把所有l(wèi)eft右邊的數都和基準值比較,獲得最左邊數在排序后位于數組中的位置(索引)
            while (left < right && array[left] <= pivot)
            {
                left++;
            }
            //將該數放到數組中的該位置
            array[right] = array[left];
        }
        //將2輪比較之后的數組的起始值再賦為基準值(已經得到最大值,并在最后一位)
        array[left] = pivot;
        //遞歸該方法(每次剔除一個排好的數)
        QuickSortArray(array, start, left - 1);
        QuickSortArray(array, left + 1, end);
    }
}


2、演示的結果圖如下

快速排序.gif

二、二分查找

1、簡介

二分查找又稱折半查找,優(yōu)點是比較次數少,查找速度快,平均性能好;其缺點是要求待查表為有序表,且插入刪除困難。因此,折半查找方法適用于不經常變動而查找頻繁的有序列表。首先,假設表中元素是按升序排列,將表中間位置記錄的關鍵字與查找關鍵字比較,如果兩者相等,則查找成功;否則利用中間位置記錄將表分成前、后兩個子表,如果中間位置記錄的關鍵字大于查找關鍵字,則進一步查找前一子表,否則進一步查找后一子表。重復以上過程,直到找到滿足條件的記錄,使查找成功,或直到子表不存在為止,此時查找不成功。簡單的來說利用的原理就是我們中學所學的二分查找,空間復雜度為O(n),時間復雜度為O(log(n))。

2、偽算法圖

二分查找.jpg.png

注意使用二分查找的數組必須是排序好的數組。

3、結合快速排序的算法寫的二分查找代碼

using System;
namespace QucikSortDemo
{
    class Program
    {
        static void Main(string[] args)
        {
            //定義數組
            int[] array = new int[] { 5, 8, 6, 1, 3, 4, 2, 7 };
            //快排
            QuickSort(array, 0, array.Length - 1);
            //二分查找
            BinSearch(array, array.Length,5);
            Console.ReadKey();
        }
        /// <summary>
        /// 二分查找
        /// </summary>
        /// <param name="array"></param>
        /// <param name="arrayLength"></param>
        /// <param name="key"></param>
        /// <returns></returns>
        static int BinSearch(int [] array,int arrayLength,int key)
        {
            //最小索引
            int low = 0;
            //最大索引
            int high = arrayLength;
            //中間索引
            int mid = (low + high) / 2;
            //直到最小索引小于最大索引跳出循環(huán)
            while (low <=high)
            {
                //若中間值為所有查找的數key
                if (array[mid] == key)
                {
                    //輸出中間數key
                    Console.WriteLine("數字{0}存在,在數組的索引為{1}", key, mid);
                    return mid;
                    
                }
                //中間數大于key時,查找左邊的數
                if (array[mid] > key)
                {
                    mid--;
                }
                //中間數小于key,查找右邊
                else
                {
                    mid++;
                }
            }
            //否則輸出無要查找的值
            Console.WriteLine("數字{0}不存在", key);
            return -1;
            
        }

        /// <summary>
        /// 快速排序算法
        /// </summary>
        /// <param name="array"></param>
        /// <param name="start"></param>
        /// <param name="end"></param>
        static void QuickSort(int [] array ,int start , int end)
        {
            int left = start;
            int right = end;
            if (start >= end)
            {
                return;
            }
            int privot = array[left];
            while (left < right)
            {
                while (left < right && array[right] >= privot)
                {
                    right--;
                }
                array[left] = array[right];
                while (left < right && array[left] <= privot)
                {
                    left++;
                }
                array[right] = array[left];
            }
            array[left] = privot;
            QuickSort(array, start, end - 1);
            QuickSort(array, start + 1, end);
        }
    }
}

最后編輯于
?著作權歸作者所有,轉載或內容合作請聯系作者
平臺聲明:文章內容(如有圖片或視頻亦包括在內)由作者上傳并發(fā)布,文章內容僅代表作者本人觀點,簡書系信息發(fā)布平臺,僅提供信息存儲服務。

推薦閱讀更多精彩內容