Я пытаюсь реализовать процедуру сортировки слиянием в C++ с использованием векторов. Но после сортировки я получаю случайные числа. Это не дает никакого предупреждения. Пожалуйста помоги. Вот мой полный код. Я пытаюсь реализовать его в классе.
#include <iostream>
#include <vector>
#include <limits>
using namespace std;
class array{
private:
vector<int> num;
public:
array();
void print();
void remove(int element);
void insert(int element);
void sort();
void mergesort(int start, int end);
void merge(int start, int end);
};
array :: array(){
cout << "Enter elements to insert in array(any character to end): ";
int element;
while(cin >> element)
num.push_back(element);
// clearing the input(cin) buffer
cin.clear();
cin.ignore(std::numeric_limits<streamsize>::max(), '\n');
}
void array :: print(){
for(unsigned int i = 0; i < num.size(); i++)
cout << "Element " << i+1 << ": " << num[i] << endl;
}
void array :: remove(int element){
for(unsigned int i = 0; i< num.size(); i++)
if(num[i] == element){
num.erase(num.begin()+i,num.begin()+i+1);
break;
}
}
void array :: insert(int element){
num.push_back(element);
}
void array :: sort(){
if(num.size() <= 1)
return;
else
mergesort(0, num.size()-1);
}
void array :: mergesort(int start, int end){
if(start >= end)
return;
else{
int mid = (start + end)/2;
mergesort(start, mid);
mergesort(mid+1, end);
merge(start, end);
}
}
void array :: merge(int start, int end){
vector<int> num2;
int mid = (start + end)/2;
int i = start;
int j = mid + 1;
cout << "start: " << start << " mid: " << mid << " end: " << end << endl;
while(i <= mid && j <= end)
num2.push_back(num[i] >= num[j] ? num[j++]: num[i++]);
if(i > mid)
while(j <= end)
num2.push_back(num[j++]);
else
while(i <= mid)
num2.push_back(num[i++]);
for(unsigned int i = 0; i <= num.size(); i++)
num[i] = num2[i];
}
Наиболее очевидной проблемой является последний цикл в merge()
for(unsigned int i = 0; i <= num.size(); i++)
num[i] = num2[i];
Индексы start
и end
передаются функциям, но этот код вслепую пытается скопировать num.size()+1
элементы из вашего временного вектора к началу num
. Я думаю, что что-то вроде этого правильнее:
for(unsigned int i = 0; i < num2.size(); i++)
num[start + i] = num2[i];
Какое "предупреждение" вы ожидали от синтаксически правильной C++ программы? Пока синтаксис верен, вы не получите никакого "предупреждения".
Итак, какая отладка вы сделали? Это первое, что вам нужно сделать.
for(unsigned int i = 0; i <= num.size(); i++) num[i] = num2[i];
У вас есть перезаписать 1 элемент здесь.
start + (end - start)/2
для расчета средней точки. Не то чтобы вы столкнулись с переполнением вероятных наборов данных, которые вы используете, но это всегда хорошая привычка. Кроме того, if-else не требуется в вашем алгоритме слияния после начального цикла. Двух конечных циклов пока достаточно. Наконец, поскольку вы все равно используете векторы, рекомендуется использовать итераторы. В любом случае, удачи.