Я недавно нашел некоторый код, где экстерн "C" был добавлен в исходном файле также для функций. Они были также добавлены в заголовочных файлах, где они были объявлены.
Я находился под предположением, что добавление 'экстерна "C" в заголовочных файлах было достаточно.
Где должен экстерн "C" блоки быть добавленным?
ОБНОВЛЕНИЕ: Предположим, что я компилирую свой код C с помощью компилятора CPP и добавил экстерна "C" защита для всех функций в заголовочных файлах (т.е. все мои функции имеют свои прототипы в заголовках), но в исходных файлах я не добавил то же. Это вызовет проблему?
Поскольку вы имеете в виду
extern "C" { ... }
стилей охранников, они объявляют некоторые функции, чтобы быть «C» связи, а не «C ++» связи (которые обычно имеют кучу дополнительного украшения имени для поддержки вещей как перегруженные функции).
Цель, конечно, состоит в том, чтобы позволить код C ++ в интерфейс с C-кодом C, который обычно находится в библиотеке. Если заголовки библиотеки не были написаны с учетом C ++, , то они не будут включать в себя Extern «C»
охранников для C ++ .
Заголовок C, написанный с помощью C ++, будет включать в себя что-то вдоль строк
#ifdef __cplusplus
extern "C" {
#endif
...
#ifdef __cplusplus
}
#endif
, чтобы программы C ++ видят правильную связь. Однако не все библиотеки были написаны с помощью C ++, поэтому иногда вам нужно сделать
extern "C" {
#include "myclibrary.h"
}
, чтобы получить правильную связь. Если файл заголовка предоставляется кем-то другим, то не очень хорошая практика, чтобы изменить его (потому что тогда вы не можете обновить его легко), поэтому лучше обернуть файл заголовка своей собственной охраной (возможно, в вашем собственном файле заголовка).
Внешний «C»
не (AFAIK) ANSI C, поэтому не может быть включен в обычный C-код без предварительно воспроцессорных охранников.
В ответ на ваше редактирование:
Если вы используете компилятор C ++, и вы объявляете функцию как Extern «C» в заголовочном файле, вам не нужно также объявлять, что функция как Extern "C" в Файл реализации. Из секции 7.5 стандарта C ++ (упор мой):
, если две объявления одинакового Функция или объект Укажите разные спецификации связи (то есть Характеристики связи этих Декларации указывают другое строковые литералы), программа неинтересно, если указаны декларации в том же единице перевода, а одно определение правила применяется, если объявления появляются в Различные переводки. Кроме Для функций с ссылками C ++, Декларация функции без связи Спецификация не должна предшествовать Первая спецификация связи для этого функция. Функция может быть объявлена без спецификации связи после Явная спецификация связи имеет был виден; Связывание явно указано в предыдущей декларации не зависит от такой функции Декларация.
Я не убежден, что это хорошая практика, хотя, поскольку есть потенциал для спецификаций связи для расхождения аварии (если, например, файл заголовка, содержащий спецификацию связи, не включен в файл реализации). Я думаю, что лучше быть явным в файле реализации.
Им нужно только пойти во все, что включено другими исходными файлами.
С некоторые идиомы Вы найдете людей, включая исходные файлы.
Я не знаю, как делать флэш-взаимодействия (и мне также интересно), но для html/javascript можно использовать Chickenfoot .
И чтобы получить безголовый + скриптовый браузер, работающий на Linux, вы можете использовать Qt webkit library . Вот пример использования .
-121--1117543-Конструктор копирования имеет следующую форму:
class example
{
example(const example&)
{
// this is the copy constructor
}
}
В следующем примере показано, где он вызывается.
void foo(example x);
int main(void)
{
example x1; //normal ctor
example x2 = x1; // copy ctor
example x3(x2); // copy ctor
foo(x1); // calls the copy ctor to copy the argument for foo
}
-121--3768770- Они должны быть добавлены ко всем файлам, которые будут включены в другие файлы.
Обычно исходные файлы не включаются.
Вы имеете в виду препроцессоры 'extern c'? Они должны быть в определении функции, а также это влияет на то, как вызов функции хранится в скомпилированном двоичном коде. Это действительно необходимо, только если Вы связываете скомпилированный c++ с c, который скомпилирован как C (в отличие от c в .cpp файле).
Вопрос изменился, чтобы было гораздо яснее, о чем он спрашивал. Этот ответ касался первоначального вопроса, когда, по крайней мере, было спорным, обсуждался ли вопрос о защите от множественного включения в заголовочные файлы - вот что касается моего ответа. Очевидно, что если бы вопрос был столь же ясен тогда, как сейчас, я бы не представил этот ответ.
Нет, нет необходимости включать охранников и в код С.
Если в заголовочном файле "header.h" говорится:
#ifndef HEADER_H_INCLUDED
#define HEADER_H_INCLUDED
...
#endif
Тогда для файла исходного текста "source.c" совершенно безопасно говорить:
#include "header.h"
Для других заголовков также безопасно включать "header.h".
Однако, люди отмечают, что открытие заголовочного файла и его чтение занимает время, что замедляет компиляцию, поэтому иногда люди делают такие вещи, как:
#ifndef HEADER_H_INCLUDED
#include "header.h"
#endif
Это означает, что если в какой-то другой заголовок, включенный в 'source.c', уже был включен 'header.h', то '#include' не перерабатывается. (Или, если 'header.h' уже был включен непосредственно в 'source.c', хотя это глупый баглет)
Так что, когда мы сталкиваемся с этим, это, скорее всего, попытка оптимизировать производительность компиляции. Отнюдь не очевидно, что это многого стоит; современные препроцессоры на Си достаточно умны в этом вопросе и, если смогут, избегут повторного включения файла. И всегда есть риск, что тест в 'source.c' имеет опечатку (#ifndef HEARER_H_INCLUDED, возможно). В этом случае тест замедляет компиляцию, так как препроцессор тестирует несущественное условие, а затем все-таки переходит на включение 'header.h'. Это 'safe'; сам заголовок защищен-- или должен быть.
Если код в 'source.c' также содержит '#define HEADER_H_INCLUDED', то возникают проблемы. #define должен быть либо до, либо после #include, и ни то, ни другое не является хорошей общей методикой.
Обратите внимание, что тело заголовка появляется после '#define HEADER_H_INCLUDED'. Это опять защита, если вложенный включает в себя 'header.h'.
Гвардии «C» имеют два целя:
Поскольку вы включаете заголовок с гвардейками «C», также в файле реализации, информация о том, как должна быть создана символы во время компиляции, доступна для компилятора, и компилятор создаст символы таким образом, что может быть используется компилятор без C ++. Следовательно, вам нужно только указать Extern «C» в файл заголовка, пока файл заголовка также включен файл реализации.