排序算法--归并排序-优化建议

时间:2025-02-04 11:29:35

1. 避免重复内存分配:每次合并时动态分配临时数组会带来性能损耗,可以预先分配一个全局临时数组,减少内存分配次数。

2. 小数组使用插入排序:当子数组规模较小时(如长度 ≤ 15),插入排序效率更高,可减少递归调用开销。

3. 非递归实现(自底向上):用循环代替递归,避免栈溢出风险,适合超大规模数据。

4. 提前检查有序性:合并前检查左右子数组是否已有序,避免不必要的合并操作。

 优化后代码:

#include <stdio.h>
#include <stdlib.h>

// 插入排序(用于小规模数据)
void insertionSort(int arr[], int left, int right) {
    for (int i = left + 1; i <= right; i++) {
        int key = arr[i];
        int j = i - 1;
        while (j >= left && arr[j] > key) {
            arr[j + 1] = arr[j];
            j--;
        }
        arr[j + 1] = key;
    }
}

// 合并函数(使用预分配临时数组)
void merge(int arr[], int temp[], int left, int mid, int right) {
    int i = left, j = mid + 1, k = left;
    while (i <= mid && j <= right) {
        if (arr[i] <= arr[j]) {
            temp[k++] = arr[i++];
        } else {
            temp[k++] = arr[j++];
        }
    }
    while (i <= mid) temp[k++] = arr[i++];
    while (j <= right) temp[k++] = arr[j++];
    // 将临时数组复制回原数组
    for (k = left; k <= right; k++) {
        arr[k] = temp[k];
    }
}

// 归并排序主函数(递归+优化)
void mergeSort(int arr[], int temp[], int left, int right) {
    const int INSERTION_THRESHOLD = 15; // 插入排序阈值
    if (right - left <= INSERTION_THRESHOLD) {
        insertionSort(arr, left, right);
        return;
    }
    
    int mid = left + (right - left) / 2;
    mergeSort(arr, temp, left, mid);
    mergeSort(arr, temp, mid + 1, right);
    
    // 检查是否已有序
    if (arr[mid] <= arr[mid + 1]) return;
    
    merge(arr, temp, left, mid, right);
}

// 封装的归并排序入口函数
void optimizedMergeSort(int arr[], int n) {
    int* temp = (int*)malloc(n * sizeof(int)); // 预分配临时数组
    if (temp == NULL) {
        printf("内存分配失败\n");
        return;
    }
    mergeSort(arr, temp, 0, n - 1);
    free(temp);
}

// 打印数组
void printArray(int arr[], int size) {
    for (int i = 0; i < size; i++) {
        printf("%d ", arr[i]);
    }
    printf("\n");
}

int main() {
    int arr[] = {12, 11, 13, 5, 6, 7, 3, 2, 8};
    int n = sizeof(arr) / sizeof(arr[0]);

    printf("排序前: ");
    printArray(arr, n);

    optimizedMergeSort(arr, n);

    printf("排序后: ");
    printArray(arr, n);

    return 0;
}

优化说明:

优化点 改进效果 适用场景
预分配临时数组 减少内存分配次数,提升性能 大规模数据排序
小数组插入排序 减少递归深度,降低函数调用开销 子数组长度 ≤ 15
提前检查有序性 避免不必要的合并操作 输入数据部分有序
入口函数封装 简化调用逻辑,隐藏临时数组细节 通用