Быстрый успешный выход из C++ с большим количеством выделенных объектов

Я ищу способ быстро выйти из С++, который выделил много структур в памяти, используя классы С++. Программа завершается правильно, но после окончательного «возврата» в программе срабатывают все автодеструкторы. Проблема в том, что программа выделила около 15 ГБ памяти через множество структур классов C++, и этот процесс автоуничтожения занимает еще около 1 часа, чтобы пройти через все структуры - хотя меня не волнуют результаты. На данный момент программе потребовался всего 1 час, чтобы выполнить задачу. Я хотел бы просто вернуться к ОС и позволить ей выполнить обычное полное удаление распределения процессов, что очень быстро. Я делал это, вручную убивая процесс на этапе очистки, но ищу лучшее программное решение.

Я хотел бы вернуть успех ОС, но мне не нужно сохранять содержимое памяти. Программа выполняет много динамического выделения/освобождения во время обычной обработки, так что это не просто управление кучей.

Есть мнения?


person bill    schedule 22.01.2011    source источник
comment
Это просто не может занять один час, если вы ничего не делаете в деструкторе. Должно быть что-то, что его блокирует. Пробовали профилировать?   -  person Naveen    schedule 22.01.2011


Ответы (6)


В стандартном C++ у вас есть только abort(), но при этом происходит сбой возврата процесса в ОС.

На многих платформах (Unix, MS Windows) вы можете использовать _exit() для выхода из программы без запуска очистки и деструкторов.

person JoergB    schedule 22.01.2011
comment
_exit() ничего не говорит о деструкторах, так как это функция POSIX (которая ничего не говорит о C++). В настоящее время он не вызывает никаких деструкторов на моей платформе, но это не гарантируется документацией. - person Öö Tiib; 22.01.2011
comment
Вот почему я сказал, что это работает на определенных платформах. Но, как обсуждалось на stackoverflow.com/q/4769229/585729, это должно иметь место на любой платформе, где она существует. - person JoergB; 22.01.2011

C++0x std::quick_exit — это то, что вам нужно, если ваш компилятор уже поддерживает его (g++-4.4.5 поддерживает).

person Maxim Egorushkin    schedule 22.01.2011

Если 15 ГБ памяти выделяются для достаточно небольшого числа классов, вы можете переопределить оператор удаления для этих классов. Просто передайте вызов стандартному удалению, но установите глобальный флаг, который, если он установлен, сделает вызов удаления неактивным. Или, если логика вашей программы такова, что эти объекты не удаляются в ходе обычного построения ваших структур данных, вы можете просто игнорировать удаление во всех случаях для этих классов.

person Paul Keister    schedule 22.01.2011

Как говорит Навин, дело не в освобождении памяти. Я писал симуляции нейронной сети с эволюционными алгоритмами, которые выделяли и освобождали много памяти маленькими и большими кусками, и это никогда не было серьезной проблемой.

person thorsten müller    schedule 22.01.2011

Если у вас есть компилятор C99, вы можете использовать функцию _Exit для немедленного завершения без глобального вызываемые деструкторы объектов или любые функции, зарегистрированные с помощью atexit; независимо от того, сбрасываются ли незаписанные данные буферизованного файла, закрываются ли открытые потоки или удаляются ли временные файлы, определяется реализацией (C99 §7.20.4.4).

Если вы работаете в Windows, вы также можете использовать ExitProcess для достижения того же эффекта.

Но, как уже говорили другие, ваши деструкторы действительно не должны работать час, если вы не выполняете достаточное количество операций ввода-вывода (запись файлов журнала и т. д.). Я настоятельно рекомендую вам профилировать вашу программу, чтобы увидеть, на что тратится время.

person Adam Rosenfield    schedule 22.01.2011

Возможные стратегии зависят от количества объектов, которые непосредственно видны в main, через которые вы получаете доступ к 15 ГБ данных, и от того, являются ли они локальными по отношению к основному или статически выделенными.

Если весь доступ к 15 ГБ данных осуществляется через локальные объекты в main, то вы можете просто заменить return 0; в конце main на exit(0);.
exit завершит ваше приложение и вызовет очистку статически выделенные переменные, но не локальные переменные.

Если доступ к данным осуществляется через несколько статически выделенных переменных, вы можете превратить их в указатели (или ссылки) на динамически выделенную память и преднамеренно слить ее.

person Bart van Ingen Schenau    schedule 22.01.2011