Шаблоны вместо препроцессора cpp, чтобы избежать линковки? - PullRequest
3 голосов
/ 23 апреля 2011

Можно ли использовать шаблоны C ++, чтобы избежать ссылок на библиотеку, содержащую функцию, которая в конечном итоге не вызывается? Например, с кодом, таким как:

template <typename T>
struct Foo {
  void bar() { zod(); }
};

int main(int argc, char *argv[])
{
  return 0;
}

GCC 4.5 отклонит его: ошибка: для «zod» нет аргументов, которые зависят от параметра шаблона, поэтому должно быть доступно объявление «zod» примечание: (если вы используете «-fpermissive», G ++ примет ваш код, но разрешить использование необъявленного имени не рекомендуется)

Является ли ошибка здесь обязательной по стандарту? Есть ли способ использовать шаблоны для достижения этой цели; и поэтому избегайте макросов cpp.

Ответы [ 3 ]

4 голосов
/ 23 апреля 2011

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

Многие реализации успешно скомпилируют и свяжут программу, которая имеет inline функций (или шаблонов), которые вызывают функции без определения. Итак, это работает просто отлично (по крайней мере, MSVC 10, GCC 4.3 и GCC 4.5):

void zod(); // we need the declaration, but no definition

inline void bar() { zod(); }

int main(int argc, char *argv[])
{
    return 0;
}

Я не уверен, что стандарт требует этого. И, конечно, он также должен работать с шаблоном вместо inline, если шаблон никогда не создается.

2 голосов
/ 23 апреля 2011

Как следует из ошибки, если zod() имеет зависимость от параметра шаблона, то SFINAE отобразит это как не проблема.

В существующем состоянии, должно быть доступно объявление zod,Извините.

Если вы управляете zod и не возражаете добавить фиктивный параметр, вы можете сделать что-то вроде этого:

template <typename T, T dummy>
struct Foo {
  void bar() { zod(dummy()); }
};

int main(int argc, char *argv[])
{
  return 0;
}

Но ... Major EW.

1 голос
/ 23 апреля 2011

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

Возможно, есть еще вопрос, которого я не вижу; Если да, отредактируйте вопрос и предоставьте более подробную информацию.

...