Переполнение стека сортировки слиянием в С++

этот код работает, когда размер массива равен 75 000, но я получаю ошибку переполнения стека, когда он равен 100 000, что я могу сделать, чтобы это исправить? Программа должна вычислить затраченное время и среднее время для обоих алгоритмов и сравнить их.

Здесь начинается ошибка

 //_______________________________
    // MERGE SORT
    void merge(int arr[], int l, int m, int r)
    {
        int i, j, k;
        int n1 = m - l + 1;
        int n2 = r - m;

        /* create temp arrays */
    int L[100000], R[100000];

    /* Copy data to temp arrays L[] and R[] */
    for (i = 0; i < n1; i++)
        L[i] = arr[l + i];
    for (j = 0; j < n2; j++)
        R[j] = arr[m + 1 + j];

    /* Merge the temp arrays back into arr[l..r]*/
    i = 0; // Initial index of first subarray
    j = 0; // Initial index of second subarray
    k = l; // Initial index of merged subarray
    while (i < n1 && j < n2)
    {
        if (L[i] <= R[j])
        {
            arr[k] = L[i];
            i++;
        }
        else
        {
            arr[k] = R[j];
            j++;
        }
        k++;
    }

    /* Copy the remaining elements of L[], if there
    are any */
    while (i < n1)
    {
        arr[k] = L[i];
        i++;
        k++;
    }

    /* Copy the remaining elements of R[], if there
    are any */
    while (j < n2)
    {
        arr[k] = R[j];
        j++;
        k++;
    }
}

подробности для публикации!..

/* l is for left index and r is right index of the
sub-array of arr to be sorted */
void mergeSort(int arr[], int l, int r)
{
    if (l < r)
    {
        // Same as (l+r)/2, but avoids overflow for
        // large l and h
        int m = l + (r - l) / 2;

        // Sort first and second halves
        mergeSort(arr, l, m);
        mergeSort(arr, m + 1, r);

        merge(arr, l, m, r);
    }
}
// END MERGE SORT
//_______________________________

Часть вставки не дает никаких ошибок на 100 000, но часть слияния делает


person Nhmanas    schedule 23.03.2018    source источник
comment
Боже мой... Может ли это быть работой для Stooge Sort?   -  person Beta    schedule 23.03.2018
comment
int L[100000], R[100000]; занимает не менее 400 000 байт на итерацию и, возможно, более полутора мегабайт. К счастью, это не рекурсивная функция, но она не оставляет вам много места для маневра. В любом случае, создайте очень маленький список, который вы хотите отсортировать, и либо начните работать с отладчиком, либо добавьте тонны операторов печати, чтобы посмотреть, что происходит.   -  person user4581301    schedule 23.03.2018


Ответы (1)


Размер стека довольно мал, поэтому попробуйте вместо этого разместить эти 2 больших массива в куче.

int *L = new int[100000];
int *R = new int[100000];

... merge stuff ...

delete [] L;
delete [] R;

Поскольку размер L равен n1, а размер R равен n2, вы можете сделать

int *L = new int[n1];
int *R = new int[n2];
person hgminh    schedule 23.03.2018
comment
Эффективность можно повысить по сравнению с этим путем выделения L и R один раз (в самом внешнем коде) и их повторного использования. - person Yakk - Adam Nevraumont; 23.03.2018
comment
Теперь выдает: Исключение: нарушение прав доступа на запись. L был 0x1118235. - person Nhmanas; 23.03.2018
comment
@user205160 user205160, не могли бы вы уточнить, как это происходит (как вы изменяете код, в какой строке происходит сбой вашей программы). Я отлично запускаю ваш код здесь - person hgminh; 23.03.2018
comment
@hgminh похоже, что он работает в вашей отредактированной версии моей, но я не думаю, что он действительно что-то делает. Функция слияния занимает всего ~ 0,01 секунды. - person Nhmanas; 23.03.2018
comment
сортировка массива с 10 ^ 5 элементами не должна занимать много времени. Вы можете попробовать увеличить до 10^7 элементов, это займет около 2 секунд (ideone.com/r52zvC) - person hgminh; 23.03.2018
comment
@hgminh ты прав! спасибо! Как я вижу здесь, я тоже должен изучать математику - person Nhmanas; 23.03.2018