BCB中的 extern “C” 【困惑】
看了一下c++中的extern “C”的作用。
//////////////人家是这么说的////////////////////////////////////////////////////////////
假设在C++中,模块A的头文件如下:
// 模块A头文件 moduleA.h
#ifndef MODULE_A_H
#define MODULE_A_H
int foo( int x, int y );
#endif
在模块B中引用该函数:
// 模块B实现文件 moduleB.cpp
#include "moduleA.h"
foo(2,3);
实际上,在连接阶段,连接器会从模块A生成的目标文件moduleA.obj中寻找_foo_int_int这样的符号!
加extern "C"声明后的编译和连接方式
加extern "C"声明后,模块A的头文件变为:
// 模块A头文件 moduleA.h
#ifndef MODULE_A_H
#define MODULE_A_H
extern "C" int foo( int x, int y );
#endif
在模块B的实现文件中仍然调用foo( 2,3 ),其结果是:
(1)模块A编译生成foo的目标代码时,没有对其名字进行特殊处理,采用了C语言的方式;
(2)连接器在为模块B的目标代码寻找foo(2,3)调用时,寻找的是未经修改的符号名_foo。
如果在模块A中函数声明了foo为extern "C"类型,而模块B中包含的是extern int foo( int x, int y ) ,则模块B找不到模块A中的函数;反之亦然。
//////////////以上人家是这么说的////////////////////////////////////////////////////////////
*************************我是这样做的**********************************
/*Unit2.h*/
#ifndef Unit2H
#define Unit2H
extern "C" int foo(int a,int b);
#endif
------------------------------------------
/*Unit2.cpp*/
#pragma hdrstop
#include "Unit2.h"
extern "C" int foo(int a,int b)
{
return a+b;
}
#pragma package(smart_init)
-----------------------------------------
/*Unit1.cpp*/
#include "Unit1.h"
#include "Unit2.h"
#pragma package(smart_init)
#pragma resource "*.dfm"
TForm1 *Form1;
__fastcall TForm1::TForm1(TComponent* Owner)
: TForm(Owner)
{
}
void __fastcall TForm1::btn1Click(TObject *Sender)
{
edt1->Text=foo(2,3);
}
--------------------------------
按照人家说的,Unit1.cpp应该找不到foo 可是我运行起来很正常,结果是对的呢!
extern c bcb c语言
[解决办法]
extern用于对全局变量或函数声明,软件看到extern就会从其它文件中查找对应的全局变量或函数定义
[解决办法]
项目包含 Unit1.cpp Unit2.cpp
这样试:
Unit1中,不要#include "Unit2.h"
Unit1中加上声明:extern "C" int foo(int a,int b); 这样就可以正常编译链接使用的。
如果去掉 "C" 声明,则链接时失败。
你上面的代码 , #include "Unit2.h" , 这样函数声明与实现是一致的,总能链接成功。
Unit2.h 中声明是 extern "C" , Unit2.cpp做函数的实现,此时函数命名就是使用 extern "C"规则编译进 Unit2.obj中。