【问题标题】:recursive merge sort repetitive element print递归合并排序重复元素打印
【发布时间】:2021-01-09 12:03:30
【问题描述】:

我在下面的代码中遇到问题... 此代码是递归合并排序,但打印的数组具有数组中的重复元素。 帮助我找出问题。

void merge(int arr[], int l, int mid, int h) {
    int i = l;
    int j = mid + 1;
    int k = l;
    int b[h + 1];
    while (i <= mid && j <= h) {
        if (arr[i] < arr[j])
            b[k++] = arr[i++];
        else
            b[k++] = arr[j++];
    }
    while (i <= mid)
        b[k++] = arr[i++];
    while (j <= h)
        b[k++] = arr[j++];
        
    for (int i = 0; i <= h; i++)
        arr[i] = b[i];
}

void Rmerge_sort(int arr[], int l, int h)
{
    if (l < h) {
        int mid = (h + l) / 2;
        Rmerge_sort(arr, l, mid);
        Rmerge_sort(arr, mid + 1, h);
        merge(arr, l, mid, h);
    }
}

int main() {
    int arr[10] = { 9, 8, 7, 6, 5, 4, 3, 2, 1, 10 }, n = 10;
    
    Rmerge_sort(arr, 0, n - 1);
   
    for (int i = 0; i < n; i++)
        cout << arr[i] << " ";
}

【问题讨论】:

    标签: recursion mergesort


    【解决方案1】:

    您定义数组b 的大小为h + 1 而不是h - l + 1。合并循环将元素复制到索引值lh,但最终的复制循环将元素从0 获取到h,从未初始化的部分复制元素。

    这是一个更正的版本:

    void merge(int arr[], int l, int mid, int h) {
        int len = h - l + 1;
        int i = l;
        int j = mid + 1;
        int k = 0;
        int b[len];
        while (i <= mid && j <= h) {
            if (arr[i] < arr[j])
                b[k++] = arr[i++];
            else
                b[k++] = arr[j++];
        }
        while (i <= mid)
            b[k++] = arr[i++];
        while (j <= h)
            b[k++] = arr[j++];
            
        for (int i = 0; i < len; i++)
            arr[l + i] = b[i];
    }
    

    但是请注意,解决此问题的更好方法是仅保存切片的左半部分以进行合并,并将h 视为切片结束后第一个元素的索引。这样可以避免混淆和容易出错的 +1/-1 调整并减少副本数量:

    void merge(int arr[], int low, int mid, int hi) {
        int len1 = mid - lo;
        int b[len1];
        int i, j, k;
    
        for (i = 0; i < len1; i++)
            b[i] = a[low + i];
    
        for (i = 0, j = mid, k = lo; i < len;) {
            if (j >= hi || arr[i] <= arr[j])
                arr[k++] = b[i++];
            else
                arr[k++] = arr[j++];
        }
    }
    
    void Rmerge_sort(int arr[], int low, int hi) {
        if (hi - low > 1) {
            int mid = low + (hi - low) / 2;  // avoid arithmetic overflow
            Rmerge_sort(arr, low, mid);
            Rmerge_sort(arr, mid, hi);
            merge(arr, low, mid, hi);
        }
    }
    
    int main() {
        int arr[10] = { 9, 8, 7, 6, 5, 4, 3, 2, 1, 10 };
        int n = sizeof(arr) / sizeof(arr[0]);
        
        Rmerge_sort(arr, 0, n);
       
        for (int i = 0; i < n; i++)
            cout << arr[i] << " ";
    }
    

    【讨论】:

      猜你喜欢
      • 2023-01-19
      • 1970-01-01
      • 2021-11-06
      • 2019-01-22
      • 1970-01-01
      • 1970-01-01
      相关资源
      最近更新 更多