从C++;代码 我有一个C函数,我想用C++调用。我无法使用“extern”C“void foo()”之类的方法,因为C函数无法使用g++编译。但它使用gcc编译得很好。如何从C++调用函数?< /p> < p>编译C代码如下:< /p> gcc -c -o somecode.o somecode.c g++ -c -o othercode.o othercode.cpp 然后是C++代码,像这样: gcc -c -o somecode.o somecode.c g++ -c -o othercode.o othercode.cpp 然后将它们链接在一起,用C++链接器: g++ -o yourprogram somecode.o othercode.o 您还必须告诉C++编译器C报头在包含C函数的声明时会出现。因此,othercode.cpp以以下内容开头: extern "C" { #include "somecode.h" }
从C++;代码 我有一个C函数,我想用C++调用。我无法使用“extern”C“void foo()”之类的方法,因为C函数无法使用g++编译。但它使用gcc编译得很好。如何从C++调用函数?< /p> < p>编译C代码如下:< /p> gcc -c -o somecode.o somecode.c g++ -c -o othercode.o othercode.cpp 然后是C++代码,像这样: gcc -c -o somecode.o somecode.c g++ -c -o othercode.o othercode.cpp 然后将它们链接在一起,用C++链接器: g++ -o yourprogram somecode.o othercode.o 您还必须告诉C++编译器C报头在包含C函数的声明时会出现。因此,othercode.cpp以以下内容开头: extern "C" { #include "somecode.h" },c++,c,linux,extern-c,C++,C,Linux,Extern C,somecode.h应包含以下内容: #ifndef SOMECODE_H_ #define SOMECODE_H_ void foo(); #endif (我在这个例子中使用了GCC,但是对于任何编译器来说,原理是一样的。分别建立C和C++,然后将它链接起来。) < P>我同意,但是在Arne Mertz的评论之后,我想给出一个完整的例子(最重要的部分是 somecode.h #ifndef H_SOMECODE #define H_SOMECODE #ifdef __cpl
somecode.h
应包含以下内容:
#ifndef SOMECODE_H_
#define SOMECODE_H_
void foo();
#endif
(我在这个例子中使用了GCC,但是对于任何编译器来说,原理是一样的。分别建立C和C++,然后将它链接起来。) < P>我同意,但是在Arne Mertz的评论之后,我想给出一个完整的例子(最重要的部分是<代码> somecode.h
#ifndef H_SOMECODE
#define H_SOMECODE
#ifdef __cplusplus
extern "C" {
#endif
void foo(void);
#ifdef __cplusplus
}
#endif
#endif /* H_SOMECODE */
somecode.c
#include "somecode.h"
void foo(void)
{
/* ... */
}
#include "foo.h"
void foo(void)
{
/* ... */
}
#include "foo.h"
#include <stdio.h>
void foo(void)
{
// modified to verify the code was called
printf("This Hello World was called in C++ and written in C\n");
}
othercode.hpp
#ifndef HPP_OTHERCODE
#define HPP_OTHERCODE
void bar();
#endif /* HPP_OTHERCODE */
#include "othercode.hpp"
#include "somecode.h"
void bar()
{
foo(); // call C function
// ...
}
extern "C" {
#include "foo.h" //a C header, so wrap it in extern "C"
}
void bar() {
foo();
}
extern "C" {
#include "foo.h" //a C header, so wrap it in extern "C"
}
int main() {
foo();
return(0);
}
othercode.cpp
#ifndef HPP_OTHERCODE
#define HPP_OTHERCODE
void bar();
#endif /* HPP_OTHERCODE */
#include "othercode.hpp"
#include "somecode.h"
void bar()
{
foo(); // call C function
// ...
}
extern "C" {
#include "foo.h" //a C header, so wrap it in extern "C"
}
void bar() {
foo();
}
extern "C" {
#include "foo.h" //a C header, so wrap it in extern "C"
}
int main() {
foo();
return(0);
}
然后按照Falken教授的指示进行编译和链接
这是因为在使用gcc
编译时,宏\uuuu cplusplus
未定义,因此somecode.c
中包含的头somecode.h
在预处理后如下所示:
void foo(void);
当使用g++
编译时,会定义\uuuucplusplus
,因此othercode.cpp
中包含的头现在如下所示:
extern "C" {
void foo(void);
}
让我从其他答案和评论中收集一些零碎的东西,给你一个干净的分离C和C++代码的例子: C部分: foo.h:
#ifndef FOO_H
#define FOO_H
void foo(void);
#endif
#ifndef FOO_H
#define FOO_H
void foo(void);
#endif
foo.c
#include "somecode.h"
void foo(void)
{
/* ... */
}
#include "foo.h"
void foo(void)
{
/* ... */
}
#include "foo.h"
#include <stdio.h>
void foo(void)
{
// modified to verify the code was called
printf("This Hello World was called in C++ and written in C\n");
}
使用gcc-c-ooo.ooo.c
编译此文件
C++部分:
bar.cpp
#ifndef HPP_OTHERCODE
#define HPP_OTHERCODE
void bar();
#endif /* HPP_OTHERCODE */
#include "othercode.hpp"
#include "somecode.h"
void bar()
{
foo(); // call C function
// ...
}
extern "C" {
#include "foo.h" //a C header, so wrap it in extern "C"
}
void bar() {
foo();
}
extern "C" {
#include "foo.h" //a C header, so wrap it in extern "C"
}
int main() {
foo();
return(0);
}
使用g++-c-obar.obar.cpp编译此文件
然后将其链接在一起:
g++ -o myfoobar foo.o bar.o
理由:
C代码应该是普通的C代码,没有表示“也许有一天我会用另一种语言调用它”的#ifdef
s。如果一些C++程序员调用C函数,那么他们的问题是怎么做的,而不是你的。如果你是C++程序员,那么C头可能不是你的,你不应该改变它,所以处理未被修改的函数名(即<代码>外部)C“< /代码>”属于C++代码。
当然,你可以编写一个方便的C++标题,除了把C标题包到一个<代码>外“C”< /> >声明中,什么也不做。这个答案是由阿恩的理论正确的一个例子启发的。一个供应商写了一个曾经支持C和C++的库;然而,最新版本仅支持C。代码中留下的以下残留指令具有误导性:
#ifdef __cplusplus
extern "C" {
#endif
这花费了我几个小时试图编译C++。简单地从C++调用C要容易得多。
ifdef__cplusplus公约违反了单一责任原则。使用此约定的代码试图同时做两件事:
- (1) 在C语言中执行函数
--而且——
- (2) 在C中执行相同的函数++
这就像试图同时用美国英语和英国英语写作一样。这是不必要地抛出一个“ifdef”Queensenglish扳手“elif”或“English扳手”,否则这是一个无用的工具,会使代码更难读懂
对于简单的代码和小型库,ifdef__cplusplus约定可能有效;然而,对于复杂的库,最好选择一种或另一种语言并坚持使用它。支持其中一种语言比同时支持两种语言需要的维护更少
这是我对Arne的代码所做的修改的记录,以使其在Ubuntu Linux上编译
foo.h:
#ifndef FOO_H
#define FOO_H
void foo(void);
#endif
#ifndef FOO_H
#define FOO_H
void foo(void);
#endif
foo.c
#include "somecode.h"
void foo(void)
{
/* ... */
}
#include "foo.h"
void foo(void)
{
/* ... */
}
#include "foo.h"
#include <stdio.h>
void foo(void)
{
// modified to verify the code was called
printf("This Hello World was called in C++ and written in C\n");
}
Makefile
# -*- MakeFile -*-
# dont forget to use tabs, not spaces for indents
# to use simple copy this file in the same directory and type 'make'
myfoobar: bar.o foo.o
g++ -o myfoobar foo.o bar.o
bar.o: bar.cpp
g++ -c -o bar.o bar.cpp
foo.o: foo.c
gcc -c -o foo.o foo.c
你能写一些代码和代码> G++> /COD>错误消息吗?如果你用C++编译器编译它,那就是C++。C代码不必用C++编译器编译。他们是不同的语言。你的代码不是有效的C++,因此没有用C++编译器编译。@ MatthieuRouget >代码>空校验,IN.C.ButoNothIn,CPLUS(sisixt大小){char变量abrththy数组[size ];} /Cord>我的尝试:<代码>空洞F(空隙*PV){int *PI= PV;*pi=42;} /Cuth.^ ^这应该是开放的,特别是当它有很好的答案时,指出C是怎样的(而不是C++)编译器可以用于C代码。@ Arne Good点。有些人在C中用C++来封装一些代码,>代码“>”C/<代码>。在“阿恩见我的答案”下面。这对我非常有用:)我收到了以下错误:错误:#337:链接规范与以前的“foo”(在第1行声明)不兼容,现在可以编译了。有人能解释一下吗?@FaizanRabbani,没有更多的细节。thb,我不喜欢C代码中的\ifdef\uu cplusplus
。C代码是较低的级别,如果某一天可能会从C++代码调用它,它就不必费心了。IMO,代码> > IFIFF < /C>只有在C++代码中才有使用,如果你想为C++中的库提供C绑定头,当然不是另一种方法.@ Pr.Fal肯,但是它是一个定义,它能够提供C++代码的“向下”兼容性,而不是C代码。1对于理性,最后对这一点有一个完全清楚的解释。非常感谢!