# включить все файлы .cpp в один модуль компиляции? - PullRequest
67 голосов
/ 13 февраля 2009

У меня недавно была причина поработать с некоторыми проектами Visual Studio C ++ с обычными конфигурациями Debug и Release, а также с «Release All» и «Debug All», которых я никогда раньше не видел.

Оказывается, у автора проектов есть единственный ALL.cpp, который #include все остальные файлы .cpp. * Все конфигурации просто создают этот файл ALL.cpp. Это, конечно, исключено из обычных конфигураций, и обычные конфигурации не собирают ALL.cpp

Мне просто интересно, было ли это обычной практикой? Какие преимущества это дает? (Моей первой реакцией было то, что пахло плохо.)

С какими подводными камнями вы можете столкнуться? Я могу подумать, что если у вас есть анонимные пространства имен в ваших .cpps, они больше не являются «приватными» для этого cpp, но теперь видны и в других cpps?

Все проекты собирают библиотеки DLL, так что наличие данных в анонимных пространствах имен не будет хорошей идеей, верно? Но функции будут в порядке?

Приветствие.

Ответы [ 5 ]

56 голосов
/ 13 февраля 2009

Некоторые называют его (и умеют обращаться с Google) как "Unity Build". Он связывает безумно быстро и достаточно быстро компилируется. Он отлично подходит для сборок, в которых вам не нужно повторяться, например, для сборки выпуска с центрального сервера, но не обязательно для инкрементной сборки.

И это PITA для поддержания.

РЕДАКТИРОВАТЬ: вот первая ссылка Google для получения дополнительной информации: http://buffered.io/posts/the-magic-of-unity-builds/

То, что делает его быстрым, заключается в том, что компилятору нужно всего лишь прочитать все, компилировать, затем связать, а не делать это для каждого файла .cpp.

Брюсу Доусону гораздо лучше написать об этом в своем блоге: http://randomascii.wordpress.com/2014/03/22/make-vc-compiles-fast-through-parallel-compilation/

47 голосов
/ 17 марта 2014

Unity повышает скорость сборки по трем основным причинам. Первая причина заключается в том, что все файлы общего заголовка должны быть проанализированы только один раз. Многие проекты C ++ имеют много заголовочных файлов, которые включены в большинство или все файлы CPP, и их избыточный анализ является основной стоимостью компиляции, особенно если у вас много коротких исходных файлов. Скомпилированные заголовочные файлы могут помочь с этой стоимостью, но обычно есть много заголовочных файлов, которые не скомпилированы заранее.

Следующая основная причина того, что Unity builds улучшает скорость сборки, заключается в том, что компилятор вызывается меньше раз. При запуске компилятора есть некоторые затраты на запуск.

Наконец, сокращение избыточного синтаксического анализа заголовка означает сокращение избыточного кода для встроенных функций, поэтому общий размер объектных файлов меньше, что ускоряет связывание.

Сборки Unity также могут дать лучший код.

Сборки Unity НЕ быстрее из-за уменьшения дискового ввода-вывода. Я профилировал многие сборки с помощью xperf и знаю, о чем говорю. Если у вас достаточно памяти, то дисковый кеш ОС избежит избыточного ввода-вывода - последующие чтения заголовка будут поступать из дискового кеша ОС. Если у вас недостаточно памяти, то единственные сборки могут даже ухудшить время сборки, в результате чего объем памяти компилятора превысит доступную память и будет выгружен.

Дисковый ввод-вывод дорог, поэтому все операционные системы активно кэшируют данные, чтобы избежать избыточного дискового ввода-вывода.

6 голосов
/ 13 февраля 2009

Интересно, пытается ли ALL.cpp поместить весь проект в одну единицу компиляции, чтобы улучшить способность компилятора оптимизировать программу под размер?

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

Тем не менее, я помню, что последние компиляторы (Microsoft, Intel, но я не думаю, что это включает в себя GCC) могут выполнять эту оптимизацию для нескольких модулей компиляции, поэтому я подозреваю, что этот «трюк» не нужен.

Тем не менее, было бы любопытно увидеть, действительно ли есть какая-то разница.

3 голосов
/ 09 июня 2014

Я согласен с Брюсом; Исходя из своего опыта, я пытался внедрить Unity Build для одного из моих проектов .dll, в котором было множество заголовков и множество .cpps; чтобы сократить общее время компиляции на VS2010 (уже исчерпаны опции инкрементной сборки), но вместо того, чтобы сократить время компиляции, у меня закончилась память, и сборка даже не смогла завершить компиляцию.

Однако добавить; Я обнаружил, что включение опции многопроцессорной компиляции в Visual Studio весьма помогает сократить время компиляции; Я не уверен, доступна ли такая опция в других компиляторах платформы.

0 голосов
/ 06 октября 2016

В дополнение к превосходному ответу Брюса Доусона следующая ссылка дает больше информации о плюсах и минусах построения единства - https://github.com/onqtam/ucm#unity-builds

...