Как я могу получить доступ к моей функции C++ в моем коде C или наоборот?
Я хочу реализовать проект в C, но удобно кодировать некоторую часть проекта в C++ а затем позвоните им из main C код.
Возможно ли это?! если да, то как я могу это сделать?!
заранее спасибо:)
П. С.
Я использовал некоторые библиотеки в моем C++ код OpenCV.
4 ответов
вам нужно будет "обернуть" ваш интерфейс C++ обычными функциями C, которые принимают параметр, чтобы указать, какой объект они будут вызваны. Например, если у вас есть в C++
class A
{
// .. boilerplate stuff...
int SomeMethod(int n, float f);
};
тогда вместе с ним вы можете объявить такую функцию, как
extern "C" int A_SomeMethod(void* Obj, int n, float f)
{
return(((A*)Obj)->SomeMethod(n, f));
}
Если вам неудобно с литьем пустоты*, вы можете реализовать какую-то карту от непрозрачного дескриптора до A*
. Но суть в том, что вам нужно будет держать вокруг некоторого дескриптора / указателя на объект что метод будет вызван. Чтобы получить указатель / дескриптор, вам нужно обернуть выделение в:
extern "C" void* A_Instantiate()
{
return new A;
}
файлы C++ должны быть скомпилированы отдельно вдоль с файлом с функциями выше. Отдельное включение для компиляции C должно включать объявления всех вышеперечисленных функций.
EDIT: предостережения и комментарии ниже важны; чтобы ответить на вопрос: "Да, можно вызвать C++ из C", и это один подход. Это не полный подход, поскольку на самом деле нет механистического способа сделать это, но это начало. Кроме того, не забудьте создать еще один звонок-через delete
, etc, etc.
Q: могу ли я получить доступ к коду C С++ или наоборот?
A: Да.
1) главное использовать extern "C" { ...}
во всех ваших заголовках для обозначения функций и данных только C, например:
http://en.wikipedia.org/wiki/Compatibility_of_C_and_C%2B%2B
/* Header file foo.h */
#ifdef __cplusplus /* If this is a C++ compiler, use C linkage */
extern "C" {
#endif
/* These functions get C linkage */
void foo();
struct bar { /* ... */ };
#ifdef __cplusplus /* If this is a C++ compiler, end C linkage */
}
#endif
2) обычный сценарий-это основная программа c++, которая вызывает смесь функций и структур C и c++. Структуры и функции объявлены в заголовках, и все они имеют "#ifdef __cplusplus / extern C".
3) Вот хороший FAQ по смешиванию C и c++:
Если строго обязателен, это только для мазохистов dyied-в-шерсти. Это потребует особой осторожности с обеих сторон и может хорошо работать сегодня и эффектно взорваться со следующим обновлением компилятора. C++ требует большой помощи во время выполнения, и получение этого для надежной работы с C обычно не поддерживается. Вы можете вызвать C из C++, который официально поддерживается (и является частью стандарта,extern "C"
и такие).
вероятно, лучше всего написать свой C в подмножестве, обрабатываемом C и c++ (отправной точкой для тонких различий является этой) и компиляции с компилятором c++. Или смиритесь с этим и решите, какой язык вам больше всего нравится.
да, вам нужно указать его как
extern "C"
таким образом, функция будет иметь связь "C", тогда код C может вызывать вашу функцию так же, как если бы она была в C. Это имя функции не будет искажено, потому что C не поддерживает перегрузку.
здесь позвольте мне процитировать @Faisal Vali:
- extern " C " -это спецификация связи
- каждый компилятор требуются обеспечить " C" связь
- спецификация связи должна выполняться только в области пространства имен
- все типы функций, имена функций и имена переменных имеют языковую связь
- два типа функций с различными языковыми связями являются различными типами, даже если в противном случае идентичны
- гнездо спецификаций рычага, внутреннее одно определяет окончательный рычаг
- extern " C " игнорируется для членов класса
- больше одной функции с определенным именем может иметь связь " C " (независимо от пространства имен)
- extern " C " заставляет функцию иметь внешнюю связь (не может сделать ее статической)
- связь с C++ с объектами, определенными на других языках, и с объектами, определенными на C++ с других языков, определяется реализацией и зависит от языка. Только там, где стратегии компоновки объектов двух языковых реализаций достаточно похожи, такая связь может быть достигнута