Модераторы: Daevaorn
  

Поиск:

Ответ в темуСоздание новой темы Создание опроса
> sort и uniq для вектора очень большого размера 
:(
    Опции темы
rudolfninja
Дата 4.2.2016, 22:23 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Опытный
**


Профиль
Группа: Участник
Сообщений: 341
Регистрация: 19.2.2013
Где: г. Минск

Репутация: 1
Всего: 6



Ребята, приветствую.

Ситуация:
есть файл, в котором содержится очень много строк (от 250 000 до 300 000). Длина строки фиксированная - 30 байтов. Мне надо эти строки обрабатывать. Строки могут повторятся, поэтому сначала я оставляю только уникальные строки.
Алгоритм такой:
1) Читаю из файла все строки в вектор:
Код

if (data.is_open())
    {
        while (!data.eof())
        {
            string str;
            data >> str;
            if (!str.empty())
                src_vec.push_back(str);
        }
        data.close();
    }


2) Сортирую вектор:
Код

sort(src_vec.begin(), src_vec.end());


3) Удаляю дубликаты строк:
Код

src_vec.resize(unique(src_vec.begin(), src_vec.end()) - src_vec.begin());


Проблема в том, что с таким количеством строк программа валится на моменте сортировки.
Вопрос вот в чем, подскажите, как можно правильно и корректно поступить в данной ситуации?
Спасибо.

P.S. В названии темы неправильно написано слово "unique". Прошу прощения. smile 

Это сообщение отредактировал(а) rudolfninja - 4.2.2016, 22:25
PM MAIL Skype   Вверх
Amp
Дата 4.2.2016, 23:17 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Опытный
**


Профиль
Группа: Участник
Сообщений: 886
Регистрация: 17.2.2009

Репутация: 3
Всего: 17



Если валится, то кэлстэк было бы неплохо приложить. Вектор у тебя из std::string? Компаратор какой-нибудь свой в std::sort передаешь?
PM MAIL   Вверх
rudolfninja
Дата 5.2.2016, 00:21 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Опытный
**


Профиль
Группа: Участник
Сообщений: 341
Регистрация: 19.2.2013
Где: г. Минск

Репутация: 1
Всего: 6



Вектор из std::string, своего компаратора никакого не писал.
Блин, сейчас на компе была запущена только студия и все нормально отработало. Буду пробовать еще раз словить падение и скину колстек.
PM MAIL Skype   Вверх
leniviy
Дата 5.2.2016, 12:14 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Опытный
**


Профиль
Группа: Участник
Сообщений: 552
Регистрация: 8.2.2003
Где: Спб

Репутация: 1
Всего: 5



Если нужен sort+uniq, то сначала сортировать, а потом выбирать uniq - плохая идея. Лучше сразу вместо вектора использовать сет.

Раз длина строк фиксированная, значит std::string не нужен. Экономнее читать каждую строку в массив байтов.


Этот ответ добавлен с нового Винграда - http://vingrad.com
PM MAIL   Вверх
Sajtran
Дата 5.2.2016, 14:31 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Новичок



Профиль
Группа: Участник
Сообщений: 10
Регистрация: 15.10.2008
Где: Мегион

Репутация: нет
Всего: 2



Цитата

   Проблема в том, что с таким количеством строк программа валится на моменте сортировки.
   

стэк для программы увеличь, QSort иногда много его жрёт или не стековую сортировку какую ни будь используй

Этот ответ добавлен с нового Винграда - http://vingrad.com
PM MAIL   Вверх
rudolfninja
Дата 5.2.2016, 19:44 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Опытный
**


Профиль
Группа: Участник
Сообщений: 341
Регистрация: 19.2.2013
Где: г. Минск

Репутация: 1
Всего: 6



Ребят, с сортировкой разобрался. Оказывается, в программе, которая генерирует данные есть возможность писать их в файл уже отсортированными =)
Всем спасибо за ответы.
Дальше слегка не по теме...
Возник такой вопрос: очень медленно отрабатывает функция erase  для вектора. Есть такой код:
Код

input curr_data, next_data;
for (int i = 0; i < input_vec.size() - 2; i++)
{
    curr_data = input_vec[i];
    next_data = input_vec[i + 1];

    if ((curr_data.chanel == next_data.chanel) && (curr_data.owner == next_data.owner) && (curr_data.wathcers == next_data.wathcers))
    {
        input_vec.erase(input_vec.begin() + (i + 1));
        i--;
    }
}

Получается, что бывают моменты, что счетчик декрементируется, тем самым увеличивая время выполнения цикла. Этот цикл отрабатывает оооочень долго  smile. Даже когда под отладчиком пошагово прохожу, то длительное время зависаю на функции erase. В теории, насколько я понимаю, после каждого удаления процесс удаления становится быстрее, т.к. количество элементов в векторе уменьшается (хотя, я не уверен в этом, т.к. не знаю как реализовано удаление в векторе), но все равно, процесс очень долгий.
Есть варианты, как ускорить все это дело? Может использовать не вектор, а что-либо еще? Просто с моим количеством записей в этом векторе (около 250тыс) удаление занимает довольно длительное время...я бы даже сказал, что выполнение этого цикла сильно тормозит работу программы.
Подскажите, пожалуйста, как ускорить сие действо?
P.S. Элементы вектора отсортированы и важно сохранить это.

Это сообщение отредактировал(а) rudolfninja - 5.2.2016, 21:11
PM MAIL Skype   Вверх
volatile
Дата 5.2.2016, 21:30 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Эксперт
****


Профиль
Группа: Завсегдатай
Сообщений: 2107
Регистрация: 7.1.2011

Репутация: 37
Всего: 85



Цитата(rudolfninja @  5.2.2016,  19:44 Найти цитируемый пост)
в программе, которая генерирует данные есть возможность писать их в файл уже отсортированными 

Если вы читаете из файла уже отсортированные, то просто изначально не добавляйте дубликаты.
(проверяйте при чтении)

PM MAIL   Вверх
xvr
Дата 8.2.2016, 12:54 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Эксперт
****


Профиль
Группа: Комодератор
Сообщений: 7046
Регистрация: 28.8.2007
Где: Дублин, Ирландия

Репутация: 60
Всего: 223



Цитата(rudolfninja @  5.2.2016,  19:44 Найти цитируемый пост)
очень медленно отрабатывает функция erase  для вектора

Это ожидаемо. vector хранит элементы в линейном масиве памяти. erase приводит к перезаписи половины элементов (в среднем)

Цитата(rudolfninja @  5.2.2016,  19:44 Найти цитируемый пост)
Может использовать не вектор, а что-либо еще?

Угу, лучше всего list. И еще лучше дать ему свой allocate, что бы элементы располагались в общем пуле памяти, а не насиловали общую кучу С++  smile 

Цитата(volatile @  5.2.2016,  21:30 Найти цитируемый пост)
Если вы читаете из файла уже отсортированные, то просто изначально не добавляйте дубликаты.

А это еще лучше  smile 

PM MAIL   Вверх
rudolfninja
Дата 8.2.2016, 13:40 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Опытный
**


Профиль
Группа: Участник
Сообщений: 341
Регистрация: 19.2.2013
Где: г. Минск

Репутация: 1
Всего: 6



В общем да, порешал проблему...чуток изменил алогритм и все летает. 
Всем спасибо.
PM MAIL Skype   Вверх
  
Ответ в темуСоздание новой темы Создание опроса
Правила форума "С++:Общие вопросы"
Earnest Daevaorn

Добро пожаловать!

  • Черновик стандарта C++ (за октябрь 2005) можно скачать с этого сайта. Прямая ссылка на файл черновика(4.4мб).
  • Черновик стандарта C (за сентябрь 2005) можно скачать с этого сайта. Прямая ссылка на файл черновика (3.4мб).
  • Прежде чем задать вопрос, прочтите это и/или это!
  • Здесь хранится весь мировой запас ссылок на документы, связанные с C++ :)
  • Не брезгуйте пользоваться тегами [code=cpp][/code].
  • Пожалуйста, не просите написать за вас программы в этом разделе - для этого существует "Центр Помощи".
  • C++ FAQ

Если Вам понравилась атмосфера форума, заходите к нам чаще! С уважением, Earnest Daevaorn

 
1 Пользователей читают эту тему (1 Гостей и 0 Скрытых Пользователей)
0 Пользователей:
« Предыдущая тема | C/C++: Общие вопросы | Следующая тема »


 




[ Время генерации скрипта: 0.0767 ]   [ Использовано запросов: 21 ]   [ GZIP включён ]


Реклама на сайте     Информационное спонсорство

 
По вопросам размещения рекламы пишите на vladimir(sobaka)vingrad.ru
Отказ от ответственности     Powered by Invision Power Board(R) 1.3 © 2003  IPS, Inc.