Какие вещи абсолютно никогда не должны быть включены в заголовочный файл?
Например, если я работаю с задокументированным форматом промышленного стандарта, который имеет много констант, будет ли хорошей практикой определять их в заголовочном файле (если я пишу парсер для этого формата)?
Какие функции должны идти в заголовочный файл?
Какие функции не должны?
Ответы:
Что положить в заголовки:
#include
директив, необходимых для того, чтобы сделать заголовок компилируемым, когда заголовок включен в некоторый исходный файл.Что не принадлежит в заголовке:
#include
директивы. Эти безвозмездные включения вызывают перекомпиляцию вещей, которые не нужно перекомпилировать, и иногда могут сделать так, чтобы система не могла компилироваться. Не#include
используйте файл в заголовке, если сам заголовок не нуждается в этом другом файле заголовка.#include
, которые могут быть изменены, или которые являются слишком большими. Эти встроенные функции должны иметь мало вентиляторов, и если у них есть вентиляторы, они должны быть локализованы в соответствии с содержимым, определенным в заголовке.Что составляет минимальный набор
#include
утверждений?Это оказывается нетривиальным вопросом. Определение TL; DR: файл заголовка должен включать файлы заголовка, которые непосредственно определяют каждый из типов, непосредственно используемых в них, или которые непосредственно объявляют каждую из функций, используемых в рассматриваемом файле заголовка, но не должны включать ничего другого. Указатель или ссылочный тип C ++ не квалифицируются как прямое использование; прямые ссылки являются предпочтительными.
Есть место для бесплатной
#include
директивы, и это в автоматическом тестировании. Для каждого заголовочного файла в программном пакете я автоматически генерирую, а затем компилирую следующее:Компиляция должна быть чистой (то есть без каких-либо предупреждений или ошибок). Предупреждения или ошибки, касающиеся неполных типов или неизвестных типов, означают, что в тестируемом заголовочном файле есть некоторые отсутствующие
#include
директивы и / или отсутствующие предварительные объявления. Обратите внимание: только то, что тесты пройдены, не означает, что набор#include
директив достаточен, не говоря уже о минимуме.источник
В дополнение к тому, что уже было сказано.
H файлы должны всегда содержать:
H-файлы никогда не должны содержать:
static
.(Я бы также сказал, что нет повода использовать непостоянные глобальные / внешние переменные, где бы то ни было, но это обсуждение другого поста.)
источник
Я, вероятно, никогда не скажу никогда, но операторы, которые генерируют данные и код при их разборе, не должны быть в файле .h.
Макросы, встроенные функции и шаблоны могут выглядеть как данные или код, но они генерируют код не при разборе, а при использовании. Эти элементы часто нужно использовать в нескольких .c или .cpp, поэтому они принадлежат .h.
На мой взгляд, заголовочный файл должен иметь минимальный практический интерфейс к соответствующему .c или .cpp. Интерфейс может включать в себя #defines, class, typedef, определения структур, прототипы функций и менее предпочтительные внешние определения для глобальных переменных. Однако, если объявление используется только в одном исходном файле, его, вероятно, следует исключить из .h и вместо этого содержать в исходном файле.
Некоторые могут не согласиться, но мой личный критерий для файлов .h состоит в том, что они #include все остальные файлы .h, которые они должны иметь возможность компилировать. В некоторых случаях это может быть много файлов, поэтому у нас есть несколько эффективных методов для сокращения внешних зависимостей, таких как прямые объявления к классам, которые позволяют использовать указатели на объекты класса, не включая то, что может быть большим деревом включаемых файлов.
источник
Заголовочный файл должен иметь следующую организацию:
Заголовочные файлы никогда не должны содержать определения объектов, только определения типов и объявления объектов.
источник
Операторы, которые генерируют данные и код при их разборе, не должны находиться в
.h
файле. Что касается моей точки зрения, заголовочный файл должен иметь только минимальный практический интерфейс к соответствующему.c
или.cpp
.источник