Форум программистов, компьютерный форум, киберфорум
Наши страницы
С++ для начинающих
Войти
Регистрация
Восстановить пароль
 
 
Рейтинг 5.00/9: Рейтинг темы: голосов - 9, средняя оценка - 5.00
MayaNash
1291 / 459 / 151
Регистрация: 24.08.2011
Сообщений: 2,245
#1

Как ускорить работу с файлами?

31.08.2016, 10:51. Просмотров 1613. Ответов 56
Метки нет (Все метки)

Предполагается, что программа будет работать с файлами размера 300-500МБ. Эти обычные функции работают слишком медленно. Может быть стоит использовать чистый С, например?
C++
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
#include <fstream>
#include <iostream>
#include <string>
#include <Windows.h>
using namespace std;
 
void merge(ifstream &f1, ifstream &f2, ofstream &fRes)
{
    string one[3], two[3];
    while (!f1.eof())
    {
        getline(f1, one[0], ':');
        getline(f1, one[1], ':');
        getline(f1, one[2]);
        
        f2.seekg(0);
        while (!f2.eof())
            
        {
            getline(f2, two[0], ':');
            getline(f2, two[1], ':');
            getline(f2, two[2]);
            if (one[1] == two[0] && one[2] == two[1])
                fRes << one[0] << ':' << two[2] << endl;
        }
    }
}
 
int main() 
{
    string file1path, file2path, fileResultPath;
    ifstream file1, file2;
    ofstream fileResult;
 
    SetConsoleCP(1251);
    SetConsoleOutputCP(1251);
 
    cout << "Путь к первому файлу > ";
    getline(cin, file1path);
    cout << "Путь ко второму файлу > ";
    getline(cin, file2path);
    cout << "Путь к файлу для записи результата > ";
    getline(cin, fileResultPath);
 
    file1.open(file1path);
    file2.open(file2path);
    fileResult.open(fileResultPath);
 
    if (file1.is_open() && file2.is_open())
    {
        merge(file1, file2, fileResult);
        cout << "Готово!\n";
    }
    else
        cout << "Проблема с открытием файлов!\n";
 
    file1.close();
    file2.close();
    fileResult.close();
 
    system("pause");
    return 0;
}

Заказываю контрольные, курсовые, дипломные и любые другие студенческие работы здесь.

1
Надоела реклама? Зарегистрируйтесь и она исчезнет полностью.
Similar
Эксперт
41792 / 34177 / 6122
Регистрация: 12.04.2006
Сообщений: 57,940
31.08.2016, 10:51
Ответы с готовыми решениями:

Как ускорить работу?
Прога ещё не доработана, сейчас интересует именно графический режим, когда...

Как ускорить работу (поиск вхождений подстроки)?
//подсчет kf int NumberKF(string &amp;P, vector&lt;string&gt; &amp; F, const int f){ int...

Можно ли как нибудь ускорить работу цикла for?
Подскажите пожалуйста - можно ли как нибудь ускорить работу цикла for? Заранее...

Подскажите пожалуйста как ускорить работу программы!
Есть задача :&quot;Во входном файле (вы можете читать данные из файла input.txt)...

Переделать работу с текстовыми файлами под работу с двоичными файлами
Здравствуйте. В этой программе идёт работа с текстовыми файлами, а нужно с...

56
Martein
675 / 86 / 15
Регистрация: 22.06.2014
Сообщений: 182
31.08.2016, 11:09 #2
1) Обычно лучше пользоваться fopen/fread/frite для C или fstream-ми для С++, т.к. они буферизируют данные (очень полезно если читаешь/пишешь небольшими порциями).
2) Если читаешь/пишешь большими кусками, кратными размеру блока на файл-системе (16/32/64/... КБ) то можно использовать WinAPI ReadFile/WriteFile. Пожалуй будет чуть побыстрее, т.к. эти ф-ции находятся ближе к моменту системного вызова и меньше кода выполниться на уровне апликации.
3) Мапируюшие ф-ции (MapViewOfFile...) обычно работают медленей обычного чтения, пользоваться ими стоит только если действительно необходимо замапировать файл в память (для простоты доступа например).

ЗЫ: Обший принцип вообще-то прост и не зависит от выбранного API: читать/писать последовательно и большими кусками.
http://forum.sources.ru/index.php?showtopic=140154#
0
nd2
2828 / 2398 / 1054
Регистрация: 29.01.2016
Сообщений: 8,022
31.08.2016, 16:17 #3
Цитата Сообщение от Керра Посмотреть сообщение
Может быть стоит использовать чистый С
Стоит, и использовать бинарный режим, даже для текстовых методов.

Добавлено через 21 минуту
Число строк в файле
1
HelicopterK52
780 / 210 / 32
Регистрация: 27.07.2016
Сообщений: 474
Завершенные тесты: 1
31.08.2016, 16:28 #4
Керра, почему бы не считать из файла сразу всё, а уже потом парсить?
Ну или если не всё, то куски побольше. Парсить чтением из файла не очень-то хорошая идея, имхо.
0
MayaNash
1291 / 459 / 151
Регистрация: 24.08.2011
Сообщений: 2,245
31.08.2016, 16:46  [ТС] #5
HelicopterK52, а как это делается?
0
Avazart
Эксперт С++
7698 / 5607 / 543
Регистрация: 10.12.2010
Сообщений: 25,182
Записей в блоге: 17
31.08.2016, 17:02 #6

Не по теме:

Цитата Сообщение от HelicopterK52 Посмотреть сообщение
Керра, почему бы не считать из файла сразу всё, а уже потом парсить?
Читаем внимательнее:
Цитата Сообщение от Керра Посмотреть сообщение
с файлами размера 300-500МБ.



Добавлено через 1 минуту
Цитата Сообщение от Керра Посмотреть сообщение
HelicopterK52, а как это делается?
Считать весь файл в std::string или std::vector если конечно оперативка позволяет.

Добавлено через 3 минуты
Цитата Сообщение от Керра Посмотреть сообщение
Может быть стоит использовать чистый С, например?
Да должно дать результат.

Добавлено через 3 минуты
Керра, Я не могу понять зачем ты делаешь f2.seekg(0); каждый раз и заново читаешь значения со второго файла?
Т.е. ты каждый раз читаешь одни и те же значения с файла?
1
HelicopterK52
31.08.2016, 17:07
  #7

Не по теме:

Цитата Сообщение от Avazart Посмотреть сообщение
Читаем внимательнее
Читаем еще внимательнее:
Цитата Сообщение от HelicopterK52 Посмотреть сообщение
Ну или если не всё, то куски побольше

0
Avazart
Эксперт С++
7698 / 5607 / 543
Регистрация: 10.12.2010
Сообщений: 25,182
Записей в блоге: 17
31.08.2016, 17:15 #8
Тут не "кусков", есть строки.

Добавлено через 7 минут
Если в файле строковые значения, то по идее можно скачать один из файлов в память полностью, возможно отсортировать строки, возможно вычислить хеши, и только потом грузить второй файл построчно и сравнивать данные с первым.
1
MayaNash
1291 / 459 / 151
Регистрация: 24.08.2011
Сообщений: 2,245
31.08.2016, 17:44  [ТС] #9
Цитата Сообщение от Avazart Посмотреть сообщение
Если в файле строковые значения, то по идее можно скачать один из файлов в память полностью, возможно отсортировать строки, возможно вычислить хеши, и только потом грузить второй файл построчно и сравнивать данные с первым.
Так и собиралась сделать
Цитата Сообщение от Avazart Посмотреть сообщение
Керра, Я не могу понять зачем ты делаешь f2.seekg(0); каждый раз и заново читаешь значения со второго файла?
Заказчик так исправил Это я, естественно, тоже исправляю, собираюсь считывать в map.
0
Ferrari F1
791 / 521 / 156
Регистрация: 27.01.2015
Сообщений: 3,025
Записей в блоге: 1
Завершенные тесты: 1
31.08.2016, 17:46 #10
Avazart, а бустовое есть что либо по файлам?
0
MayaNash
1291 / 459 / 151
Регистрация: 24.08.2011
Сообщений: 2,245
31.08.2016, 17:47  [ТС] #11
Ну в общем попробую считывать все из первого файла с помощью С-шных функций в map map-ов, раз там два идентификатора (там не обязательно числа), и посмотрим что получится.
0
Avazart
Эксперт С++
7698 / 5607 / 543
Регистрация: 10.12.2010
Сообщений: 25,182
Записей в блоге: 17
31.08.2016, 18:01 #12
Цитата Сообщение от Керра Посмотреть сообщение
Заказчик так исправил Это я, естественно, тоже исправляю, собираюсь считывать в map.
Можно не в map, а в отсортированный вектор и binary_search() для поиска.

Добавлено через 3 минуты

Не по теме:

Цитата Сообщение от Ferrari F1 Посмотреть сообщение
Avazart, а бустовое есть что либо по файлам?
Хз, думаю нет.



Ну еще если извратится можно попробовать развести по потокам само сравнение.
Т.е. считать 2000 строк, потом дать каждому потоку по 1000 строк для парсинга/поиска/сравнения в данными второго файла, по завершению соединить результаты и записать в результирующий файл.
1
MayaNash
1291 / 459 / 151
Регистрация: 24.08.2011
Сообщений: 2,245
31.08.2016, 18:02  [ТС] #13
Avazart, благодарю
0
Mr.X
Эксперт С++
3178 / 1705 / 435
Регистрация: 03.05.2010
Сообщений: 3,867
31.08.2016, 19:41 #14
Цитата Сообщение от Керра Посмотреть сообщение
Предполагается, что программа будет работать с файлами размера 300-500МБ. Эти обычные функции работают слишком медленно.
А в чем задача-то? Что вы хотите с ними сделать?
0
MayaNash
1291 / 459 / 151
Регистрация: 24.08.2011
Сообщений: 2,245
31.08.2016, 21:15  [ТС] #15
Mr.X, есть два файла. В первом файле строки вида "строка1:идентификатор1:идентификатор2", во втором "идентификатор3:идентификатор4:строка2". Если идентификатор1 = идентификатор3 и идентификатор2 = идентификатор4, то в третий файл нужно записать "строка1:строка2". Вот, собственно, и все. Но вроде уже разобрались.

Добавлено через 44 секунды
Искать нужно все совпадения идентификаторов. Вот.

Добавлено через 29 минут
Цитата Сообщение от nd2 Посмотреть сообщение
использовать бинарный режим, даже для текстовых методов
Тогда получается что нужно посимвольно? А оно не медленнее чем чтение таки в текстовом режиме?
0
Nosey
1350 / 401 / 144
Регистрация: 22.10.2014
Сообщений: 863
Завершенные тесты: 2
31.08.2016, 21:49 #16
Цитата Сообщение от Керра Посмотреть сообщение
В первом файле строки вида "строка1:идентификатор1:идентификатор2", во втором "идентификатор3:идентификатор4:строка2". Если идентификатор1 = идентификатор3 и идентификатор2 = идентификатор4, то в третий файл нужно записать "строка1:строка2"
Так бы сразу и сказали )
Да без проблем
2
MayaNash
1291 / 459 / 151
Регистрация: 24.08.2011
Сообщений: 2,245
31.08.2016, 21:51  [ТС] #17
О господи)))
Я из тех людей, которым лучше чтобы им сказали с помощью чего решить задачу, а не решили за них))) Мне тут долго разбираться, я еще совсем студентка)))

Добавлено через 17 секунд
Большое спасибо, конечно
1
Nosey
1350 / 401 / 144
Регистрация: 22.10.2014
Сообщений: 863
Завершенные тесты: 2
31.08.2016, 21:59 #18
Цитата Сообщение от Керра Посмотреть сообщение
Я из тех людей, которым лучше чтобы им сказали с помощью чего решить задачу, а не решили за них)))
1) Читаем из файлов в std::map<std::pair<std::string, std::string>, std::string>.
2) для быстрого чтения файла в память используем это: std::string fileString1 { std::istreambuf_iterator<char> { f1 }, std::istreambuf_iterator<char> { } };.
3) Для поиска "подстроки" используем это std::find(begin, std::end(fileString1), ':');.
4) Потом проходим по одной мапе заглядывая в другую и выводим результат в файл. Примерно так:
C++
1
2
3
4
5
6
7
8
for (auto& fd1 : fileData1)
    {
        const auto& fd2 = fileData2.find(fd1.first);
        if (fd2 != std::end(fileData2))
        {
            fRes << fd1.second << ':' << fd2->second << std::endl;
        }
    }
1
Avazart
31.08.2016, 22:06
  #19

Не по теме:

Nosey, Для вновь понаехавших:

Цитата Сообщение от Керра Посмотреть сообщение
работать с файлами размера 300-500МБ.
Cтоит быть осторожнее с такими объемами памяти, тем более как вы описываете.
И вообще то как вы описываете можно сразу set использовать.

0
Nosey
1350 / 401 / 144
Регистрация: 22.10.2014
Сообщений: 863
Завершенные тесты: 2
31.08.2016, 22:14 #20
Цитата Сообщение от Avazart Посмотреть сообщение
Cтоит быть осторожнее с такими объемами памяти, тем более как вы описываете.
Да, про память забыл сказать, после парсинга строки в мапу - строку убиваем, за ненадобностью, или можно использовать [boost|std]::string_view.

Не по теме:

Цитата Сообщение от Avazart Посмотреть сообщение
И вообще то как вы описываете можно сразу set использовать.
Но тогда неубодно в одну функцию влезть :)

0
31.08.2016, 22:14
MoreAnswers
Эксперт
37091 / 29110 / 5898
Регистрация: 17.06.2006
Сообщений: 43,301
31.08.2016, 22:14

Динамический массив, много циклов и простые числа. Как ускорить работу программы ?
Всем привет. Задание следующее: Кто нибудь вводит с клавиатуры число n и k,...

Ускорить работу программы
Лексикографический порядок чисел (Время: 1 сек. Память: 16 Мб Сложность:...

Ускорить работу функций
Здравствуйте. Не подскажете как можно ускорить работу функций в цикле? А то...


Искать еще темы с ответами

Или воспользуйтесь поиском по форуму:
20
Ответ Создать тему
Опции темы

КиберФорум - форум программистов, компьютерный форум, программирование
Powered by vBulletin® Version 3.8.9
Copyright ©2000 - 2018, vBulletin Solutions, Inc.
Рейтинг@Mail.ru