Пытаюсь решить задачу о сортировке миллиона 32 битных int'ов с ограничением по оперативной памяти (
habrahabr.ru/post/65503/) В качестве языка реализации использую C++.
С первой частью алгоритма проблем не возникло: считываем кусок данных из входного файла, сортируем и записываем во временный файл.
А вот со второй частью у меня проблемы. Вот кусок кода, который отвечает за чтение временных файлов в буфер и их слияние:
bool NumbersProcessor::readSortFile(ifstream &file, vector<int> &data) {
int tmp;
for (int i = 0; (i < bufferSize && file >> tmp); i++)
data.push_back(tmp);
return file.good();
}
void NumbersProcessor::mergeFiles(int numFiles) {
ifstream inputFile1, inputFile2;
ofstream temp;
string fileName1, fileName2;
int i = 0;
int k = 0;
int max = numFiles - 1;
bool file1Good, file2Good;
vector<int> data1;
vector<int> data2;
while(max >= 2) {
fileName1 = "tempfile_"; fileName1 += to_string(i);
fileName2 = "tempfile_"; fileName2 += to_string(i+1);
try {
inputFile1.open(fileName1);
inputFile2.open(fileName2);
} catch(int e) {
cout << "Could not open the open the files!\nError " << e;
}
file1Good = true;
file2Good = true;
while(file1Good || file2Good) {
if(data1.size() == 0)
file1Good = readSortFile(inputFile1, data1);
if(data2.size() == 0)
file2Good = readSortFile(inputFile2, data2);
temp.open("temp", ios::app);
std::merge(data1.begin(),
data1.end(),
data2.begin(),
data2.end(),
std::ostream_iterator<int>(temp, "\n"));
temp.close();
data1.clear();
data2.clear();
}
inputFile1.close();
inputFile2.close();
remove(fileName1.c_str());
remove(fileName2.c_str());
fileName1 = "tempfile_"; fileName1 += to_string(k);
rename("temp", fileName1.c_str());
i = i + 2;
k++;
if (i >= max) {
max = max / 2 + max % 2;
i = 0;
k = 0;
}
}
cout << endl;
}
Слияние файлов работает, но не совсем корректно. Если взять последовательность из десяти чисел
7 2 6 5 9 7 8 1 4 3 и размер буффера равный двум числам, то на выходе получим:
1 2 3 4 5 7 6 7 8 9
Аналогичная ситуация наблюдается и для более длинных последовательностей: в начале и конце последовательности числа стоят в правильном порядке, но ближе к середине результат неправильный. Что я делаю не так?