7

*.h или *.hpp для определения ваших классов?

1

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

Какие преимущества и недостатки использования .hpp по сравнению с .h?

5 ответ(ов)

7

Вот несколько причин, по которым заголовки для C и C++ могут иметь разные имена:

  • Автоматическое форматирование кода: У вас могут быть разные руководства по форматированию для C и C++ кода. Если заголовки разделены по расширению, вы можете настроить свой редактор так, чтобы он автоматически применял соответствующее форматирование.

  • Именование: Я участвовал в проектах, где использовались библиотеки, написанные на C, а затем были реализованы обертки на C++. Поскольку заголовки обычно имели схожие названия, например, Feature.h и Feature.hpp, их легко было различить.

  • Включение заголовков: Возможно, что в вашем проекте доступны более подходящие версии заголовков, написанные на C++, но вы используете версию на C (см. предыдущий пункт). Если заголовки названы в соответствии с языком, на котором они написаны, вы можете легко выделить все заголовки на C и проверить наличие их C++ версий.

Помните, что C это не C++ и смешивание этих языков может быть очень опасным, если вы не знаете, что делаете. Подходящее именование ваших исходников помогает различать языки.

3

Я использую расширение .hpp, потому что хочу, чтобы пользователь мог различать, какие заголовки являются заголовками C++, а какие — заголовками C.

Это может быть важно, когда ваш проект использует как модули C, так и C++: как кто-то уже объяснял ранее, подходить к этому нужно очень осторожно, и всё начинается с "контракта", который вы предлагаете через расширение.

.hpp : Заголовки C++

(Или .hxx, или .hh, или любое другое)

Этот заголовок предназначен только для C++.

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

.h : Совместимые заголовки C/C++ или чисто C-заголовки

Этот заголовок может быть включён как из исходного файла на C, так и из исходного файла на C++, прямо или косвенно.

Он может быть включён напрямую, защищённый макросом __cplusplus:

  • Это значит, что с точки зрения C++ код, совместимый с C, будет определён как extern "C".
  • С точки зрения C весь C-код будет очевиден, но C++ код будет скрыт (поскольку он не скомпилируется в компиляторе C).

Например:

#ifndef MY_HEADER_H
#define MY_HEADER_H

   #ifdef __cplusplus
      extern "C"
      {
   #endif

   void myCFunction();

   #ifdef __cplusplus
      } // extern "C"
   #endif

#endif // MY_HEADER_H

Или его можно включить косвенно через соответствующий заголовок .hpp, который обернёт его в объявление extern "C".

Например:

#ifndef MY_HEADER_HPP
#define MY_HEADER_HPP

extern "C"
{
#include "my_header.h"
}

#endif // MY_HEADER_HPP

А также:

#ifndef MY_HEADER_H
#define MY_HEADER_H

void myCFunction();

#endif // MY_HEADER_H
0

Я всегда рассматривал расширение .hpp как некий «смешанный» вариант для файлов .h и .cpp... это заголовочный файл, который содержит также детали реализации.

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

0

Не имеет значения, какое расширение использовать. Оба варианта подходят.

Я использую *.h для C и *.hpp для C++.

0

EDIT [Добавлено предложение от Дэна Ниссенбаума]:

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

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

Другая конвенция предполагает использование .h для C-заголовков и .hpp для C++; хорошим примером является библиотека Boost.

Цитата из FAQ Boost:

Расширения файлов сообщают о "типе" файла как для людей, так и для компьютерных программ. Расширение '.h' используется для заголовочных файлов C, и, следовательно, передает неправильную информацию о заголовочных файлах C++. Использование без расширения ничего не сообщает и заставляет проверять содержимое файла для определения типа. Использование '.hpp' однозначно идентифицирует его как заголовочный файл C++, и это хорошо работает на практике. (Рейнер Дейк)

Чтобы ответить на вопрос, пожалуйста, войдите или зарегистрируйтесь