Quick Sort prove safety Offer-

Quick sort of Partition functions on Offer to prove safety and I learned a data structure of the book is not the same, and therefore want to explore the two different treatment under.

1. The basic idea

The basic idea of ​​quick sort is based on divide and conquer. In the sort table to be L [1 ... n] take any of a pivot element as a reference, to be sorted by the sorting trip table is divided into two independent parts L [1 ... k-1] and L [k + 1 ... n], such that L [1 ... k-1] is less than all the elements pivot, L [k + 1 ... n] is greater than or equal to all elements in the pivot, the pivot placed on its end position L (k) on. Then the process is repeated recursively on the two sub-tables, until only a portion of each of the inner element up or empty, i.e. all elements in its final position.

2. Offer to prove safety on the Partition achieve

// Partition为分割函数, length表示data数组的长度
int Partition(int data[], int length, int low, int high) {
    if (data == nullptr || length <= 0 || low < 0 || high >= length) {
        return 1;
    }
    
    // 在[low, high]区间中随机取一个基准值,并将其换到区间最末尾
    int index = RandomInRange(low, high);
    Swap(&data[index], &data[high]);
    
    // small在low的前面一位
    int small = low - 1;
       
    for (index = low; index < high; ++index) {
        if (data[index] < data[high]) {
            // ++small后表示大于基准值的第一个数的下标
            // 如果不存在大于基准值的数,则表示当前比较的数字下标
            ++small;

            // 交换后的small表示小于基准值的最后一个数字的下标
            if (small != index) {
                Swap(&data[index], &data[small]);
            }
        }
    }
    
    // ++small后表示大于基准值的第一个数的下标
    ++small;
    Swap(&data[small], &data[high]);
    
    return small;
    
}

Quicksort Other functions implemented as follows:


// 生成一个随机数,范围在[low,high),是一个前闭后开的区间
int RandomInRange(int low, int high) {
    return rand() % (high - low) + low;
}

// 交换两个整数
void Swap(int* left, int* right) {
    int temp  = *left;
    *left = *right;
    *right = temp;
}

// 快速排序函数
void QuickSort(int data[], int length, int low, int high) {
    if (low == high) {
        return;
    }
    
    int index = Partition(data, length, low, high);
    
    if (index > low) {
        QuickSort(data, length, low, index - 1);
    }
    
    if (index < high) {
        QuickSort(data, length, index + 1, high);
    }
}

// 数据打印
void PrintData(int data[], int length) {
    for (int i = 0; i < length; ++i) {
        std::cout << data[i] << " ";
    }
    
    std::cout << std::highl;
}

int main() {
    // 以系统时间作为随机函数种子
    srand((unsigned)time(nullptr));

    int const length = 10;
    
    int data[length];

    // 生成随机数
    for (int i = 0; i < length; ++i) {
        data[i] = RandomInRange(1, length*length);
    }
    
    // 打印生成的随机数
    PrintData(data, length);
    
    // 调用快排函数进行排序
    QuickSort(data, length, 0, length - 1);
  
    // 打印快速排序后的数
    PrintData(data, length);
    
    return 0;
    
}

The initial order is {49, 38, 65, 97, 76, 13, 27}, the reference value of the first pass 49 quicksort data implementation is as follows:

step small index
0 49 38 65 97 76 13 27
1 27 38 65 97 76 13 49
2 0 0 27 38 65 97 76 13 49
3 1 1 27 38 65 97 76 13 49
4 1 2 27 38 65 97 76 13 49
5 1 3 27 38 65 97 76 13 49
6 1 4 27 38 65 97 76 13 49
7 2 5 27 38 13 97 76 65 49
8 3 6 27 38 13 49 76 65 97

After completion of the first pass sort reference values ​​{27, 38, 13} smaller than before 49 49, {76, 65, 97} 49 large than 49 after the reference value.

3. Partition materials on the general implementation

// Partition为分割函数
int Partition(int data[], int low, int high) {

    // 将当前表中第一个元素设为基准值,对表进行划分
    int pivot = data[low]; 

    // 循环跳出条件
    while (low < high) {
        while (low < high && data[high] >= pivot) {
            --high;
        }

        // 将比基准值小的元素移动到左端
        data[low] = data[high];

        while (low < high && data[low] <= pivot) {
            ++low;
        }

        // 将比基准值大的元素移动到右端
        data[high] = data[low];
    }

    // 基准元素存放到最终位置
    data[low] = pivot;

    // 返回存放基准值的最终位置
    return low;
}

Quicksort Other functions implemented as follows:

void QuickSort(int data[], int low, int high) {
    // 递归跳出条件
    if (low < high) {
        // 将data[low...high]一分为二,pivotpos是基准值
        int pivotpos = Partition(data, low, high);

        // 对左子表进行递归排序
        QuickSort(data, low, pivotpos - 1);

        // 对右子表进行递归排序
        QuickSort(data, pivotpos + 1, high);
    }
}

The initial order is {49, 38, 65, 97, 76, 13, 27}, the reference value of the first pass 49 quicksort data implementation is as follows:

step low high
0 0 6 49 38 65 97 76 13 27
1 2 6 27 38 65 97 76 13 27
2 2 6 27 38 65 97 76 13 65
3 2 5 27 38 13 97 76 13 65
4 3 5 27 38 13 97 76 97 65
5 3 2 27 38 13 49 76 97 65

After completion of the first pass sort reference values ​​{27, 38, 13} smaller than before 49 49, {76, 97, 65} 49 large than 49 after the reference value.

4. Summary

As can be seen, the process of the above-described operation results in two ideas are different, the former is smaller than the standard used to refer to small elements rightmost position, the switching operation carried out to ensure that during traversal left small elements are less than standard element, while the latter is low, high, respectively represent the set of boundary positions below and above the reference value, the latter more easy to understand.


Homepage:

www.codeapes.cn

Guess you like

Origin www.cnblogs.com/codeapes666/p/12089185.html