Является ли "встроенный" неявным в функциях-членах C ++, определенных в определении класса - PullRequest
36 голосов
/ 08 февраля 2012

Согласно спецификации C ++, следующие два класса одинаково определены?

class A
{
   void f()
   {
   }
};

class B
{
   inline void f()
   {
   }
};

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

Следующий вопрос: Предполагая, что для стиля кода избыточно, было бы разумно сохранить тег «inline», поэтому будущий разработчик понимает, что функция должна быть встроенной, и не удаляет определение где-либо еще и удаляет встраивание

Спасибо:)

Ответы [ 4 ]

87 голосов
/ 08 февраля 2012

Стандарт C ++ ISO гласит:

"Функция, определенная в определении класса, является встроенной функцией."

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

19 голосов
/ 08 февраля 2012

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

Ключевое слово inline не имеет никакого отношения к встраиванию.Речь идет о том, разрешено ли несколько идентичных определений функции в разных TU.Если кто-то перемещает определение функции в другое место, он должен решить, следует ли пометить его inline на следующей основе:

  • Если оно находится в файле .cpp для этого класса, тодопустимо пометить его inline, если он вызывается только из этого TU.Тогда, вероятно, не имеет значения, помечен ли он inline или нет, но вы можете пометить его inline как подсказку компилятора, если считаете, что компилятор будет обращать внимание на то, что вы хотите.

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

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

9 голосов
/ 08 февраля 2012

ставит ли "встроенный" квалификатор для такой функции-члена, определенной в определении класса, полностью излишним?

Да

Для стиля кода было бы разумно сохранить тег "inline", чтобы будущий разработчик понял, что функция должна быть встроенной, и не удаляет определение где-либо еще и не удаляет встраивание?

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

Так что, если вам это не нужно, удалите его. Если вам нужно, поместите его туда (если вы забудете, компилятор сообщит вам об этом).

2 голосов
/ 08 февраля 2012

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

Что касается того, стоит ли оставлять это там - я так не думаю. Было бы лучше дать подробный комментарий, объясняющий, почему функция ДОЛЖНА быть встроена (из которых я могу выделить только две причины: либо «это шаблон», в этом случае выход из подкладки невозможен, либо «производительность», в этом случае Я хотел бы увидеть некоторые подтверждающие доказательства, а не «он должен работать лучше, потому что он встроен», который я видел в некоторых местах.

...