@maybe_a_rat_fucker

Как работает рекурсия, и как мне исправить код?

Пишу код для быстрой сортировки данных на c++. Не могу понять как работает рекурсия, к тому же вылазит сообщение об ошибке: Exception thrown at 0x00007FF6637D6BF8 in Testing.exe: 0xC0000005: Access violation reading location 0x00000006D7D00000. Хотелось бы, чтобы кто-нибудь помог с этим и с пониманием как работает рекурсия.
#include <iostream>



using namespace std;


void quicksort(int* array, int size_of_array) {
	int id_last_element = size_of_array - 1;
	int id_first_element = 0;
	int flag = 1;
	int pivot = 0;
	while (id_first_element != id_last_element)
	{
		if (flag % 2 != 0)
		{
			if (array[pivot] > array[id_last_element])
			{
				cout << array[pivot] << " change on " << array[id_last_element] << endl;
				swap(array[pivot], array[id_last_element]);
				pivot = id_last_element;
				cout << "Array: ";
				for (int k = 0; k < size_of_array; k++)
				{
					cout << array[k] << " ";
				}
				cout << endl;
				id_first_element++;
				flag++;
			}
			else {
				id_last_element--;
			}
		}
		else if (flag % 2 == 0)
		{
			if (array[pivot] < array[id_first_element])
			{
				cout << array[pivot] << " CHANGE ON " << array[id_first_element] << endl;
				swap(array[pivot], array[id_first_element]);
				pivot = id_first_element;
				for (int k = 0; k < size_of_array; k++)
				{
					cout << array[k] << " ";
				}
				cout << endl;
				id_last_element--;
				flag++;
			}
			else {
				id_first_element++;
			}
		}
	}

	if (id_last_element > 0) 
	{
		quicksort(array, id_last_element + 1);
	}
	if (id_first_element <= size_of_array)
	{
		quicksort(array, size_of_array - id_first_element);
	}
}



int main()
{
	setlocale(LC_ALL, "Rus");
	int array_1[10] = { 5,3,8,2,6,9,1,7,4,10 };

	int array_size = end(array_1) - begin(array_1);


	cout << "Unsorted array:";
	for (int i = 0; i < array_size; i++)
	{
		cout << array_1[i] << " ";
	}
	cout << endl;

	quicksort(array_1, array_size);


	cout << "result is:" << endl;
	for (int j = 0; j < array_size; j++)
	{
		cout << array_1[j] << endl;
	}
	system("pause");
	return 0;
}
  • Вопрос задан
  • 143 просмотра
Решения вопроса 1
wataru
@wataru Куратор тега C++
Разработчик на С++, экс-олимпиадник.
Код разбиения у вас неверный. Забейте пока на рекурсию, отладьте код до рекурсивных вызовов.

Во-первых, удалите flag. Ужасный, отвратительный подход. Что он означает? Зачем он вам нужен? Разве нельзя обе части выполнять в цикле всегда, вместо того, что бы чередовать их очень не читаемым и запутанным методом?

Далее, надо поддерживать какой-то инвариант. У вас там 2 переменные в цикле first и last. Что вы поддерживаете? Все элементы до first не превосходят pivot, а все после last не меньше его? Определитесь с этим и докажите себе, что после каждой итерации цикла этот инвариант сохранится. Вместо того, чтобы следить за тем, где у вас ведущий элемент, просто запомните в переменную его значение.

Если не разберетесь, смотрите на код в википедии, например.
Ответ написан
Пригласить эксперта
Ваш ответ на вопрос

Войдите, чтобы написать ответ

Войти через центр авторизации
Похожие вопросы