——C++编译器完全兼容C语言的编译方式。(但是得有源代码)

——C++编译器会优先使用C++的编译方式进行编译

——extern "C" 关键字能够强制C++编译器进行C方式的编译

  学习目标:实现C语言与C++之间的互相调用

       学习 extern "C" {} 关键字

       学习 __cplusplus标准宏

实验一、通过C++调用C编译器编译出来的   .o  文件 (extern "C" 关键字使用)

  1、创建文件:add.c    

int add(int a,int b)
{
return a+b;
}  

  2、创建:add.h  

int add(int a,int b);//对函数进行声明

  3、使用C编译进行add.c 进行编译 gcc -c add.c -o add.o 生成.o文件   nm add.o //add.o中的符号表信息 

 T add

  4、创建:main.cpp  

  #include <stadio.h>
#include "add.h"
int main(int argc, char *argv[])
{
printf("Begin...\n");
int c = ;
c = add(,)
printf("c = %d\n",c);
printf("End...\n");
return ;
}

  5、编译:g++ main.cpp add.o

  输出错误信息:
/tmp/cc6HoeKB.o: In function `main':
main.cpp:(.text+0x2d): undefined reference to `add(int, int)'
collect2: error: ld returned exit status

  从上面错误可以看出 add 这个函数是没有定义的。

  6、修改main.cpp 使用关键字  extern "C" {需要编译器进行C方式编译的部分}  

  #include <stadio.h>
extern "C"
{
#include "add.h"
}
int main(int argc, char *argv[])
{
printf("Begin...\n");
int c = ;
c = add(,)
printf("c = %d\n",c);
printf("End...\n");
return ;
}

  

  编译:g++ main.cpp add.o
  编译成功。
  运行结果:  

  Begin...
  c =
  End...

 

实验2 _Cplusplus关键字使用,__cplusplus关键字 是C++编译器内置的标准宏定义

  确保C代码能够以统一的方式被编译成目标文件。  

#include <stdio.h>
#ifdef __cplusplus //如果 __cplusplus被定义 ,__cplusplus只有C++中才有 成立则表示为C++编译器
//使用__cplusplus来判定是否需要将 extern "C"{}加入到编译中来。实现同一段代可以使用C、C++编译器编译
extern "C"
{
#endif #include "add.h" #ifdef __cplusplus
}
#endif int main(int argc, char *argv[])
{
printf("Begin...\n");
int c = ;
c = add(,);
printf("c = %d\n",c);
printf("End...\n");
return ;
}

  注意:C++编译器不能以C的方式来编译重载函数。

      编译方式决定函数名被编译后的目标名(C 目标名.o  C++ .oo)

      C++编译方式将 函数名  参数列表  编译成  目标名

      C编译方式只将 函数名 作为目标 (所以对应上了C++编译器不能以C的方式来编译重载函数。这句话)

实验三、使用C来调用C++编译的目标文件(.oo)

    1、创建add.cpp    

#include "add.h"

int add(int a,int b)
{
return a+b;
}

  2、创建add.h头文件  

#ifdef __cplusplus//如果是C++编译器
extern "C"{//下面部分使用C语言的编译方式进行编译
#endif int add(int a,int b);
#ifdef __cplusplus
}
#endif

  3、编译add.cpp 目标文件 g++ -c add.c -o add.oo

  4、创建main.c    

#include <stdio.h>
#include "add.h" int main(int argc, char *argv[])
{
int c = ;
printf("Begin...\n");
c = add(,);
printf("c = %d\n",c);
printf("End...\n");
return ;
}

  5、编译C程序生成.out 文件  gcc main.c add.oo

  6、运行结果:  

Begin...
c =
End...

小结:

  使用C语言来调用C++关键还是在 extern "C" {} 关键字。强制C++编译器使用C语言的方式来编译{}内的代码。

  只有C++编译出来的文件支持C语言调用才行。

C++ 调用C语言、extern "C"、__cplusplus关键字的更多相关文章

  1. JAVA调用C语言写的SO文件

    JAVA调用C语言写的SO文件 因为工作需要写一份SO文件,作为手机硬件IC读卡和APK交互的桥梁,也就是中间件,看了网上有说到JNI接口技术实现,这里转载了一个实例 // 用JNI实现 // 实例: ...

  2. C++中extern “C”含义及extern、static关键字浅析

    https://blog.csdn.net/bzhxuexi/article/details/31782445 1.引言 C++语言的创建初衷是“a better C”,但是这并不意味着C++中类似C ...

  3. Java语言与C语言混合编程(2)--在Java中调用C语言本地库

    在上一篇文章中介绍了Java语言中的native关键字,以及Java语言调用C语言的编译生成本地动态链接库(DLL)实现加法运算的小例子,本文通过一个更加详细的例子,深入讲解Java语言调用C语言的函 ...

  4. 通过实例简介python使用ctypes模块调用C语言动态库

    看介绍python语言时,说它是胶水语言,可以调用其他语言.通过使用ctypes模块就可以调用C语言的动态库.下面先放上官方文档和几个比较好的博文. 1.官方文档:http://python.net/ ...

  5. java jni 调用c语言函数

    今日在hibernate源代码中遇到了native关键词,甚是陌生,就查了点资料,对native是什么东西有了那么一点了解,并做一小记. native关键字说明其修饰的方法是一个原生态方法,方法对应的 ...

  6. 分享:写了一个 java 调用 C语言 开发的动态库的范例

    分享:写了一个 java 调用 C语言 开发的动态库的范例 cfunction.h   代码#pragma once#ifdef __cplusplusextern "C" {#e ...

  7. Java如何调用C语言程序,JNI技术

    Java为什么要调用C语言编写的程序因为涉及操作系统底层的事件,Java是处理不了的,例如用户上传一个视频文件,需要后台给视频加上水印,或者后台分离视频流和音频流,这个事Java就做不了,只能交给C语 ...

  8. C语言入门:03.关键字、标识符、注释

    一.学习语法之前的提醒 (1)C语言属于一门高级语言,其实,所有高级语言的基本语法组成部分都是一样的,只是表现形式不太一样 (2)就好像亚洲人和非洲人,大家都有人类的结构:2只 手.2只脚.1个头,只 ...

  9. 在Windows Phone项目中调用C语言DLL

    在Windows Phone项目中调用C语言写的DLL 最近接到一个需求,需要在WP里调用一个C语言写的DLL,并且说Android和iOS都可以,问我WP是否可以这样? 我说我调研一下,就有了下面的 ...

随机推荐

  1. 分布式-信息方式-ActiveMQ的Destination高级特性3

    虚拟destination用来创建逻辑destination,客户端可以通过它来生产和消费消息,它会把消息映射到物理destination. ActiveMQ支持2种方式: 1:虚拟主题(Virtua ...

  2. C++入门经典-例3.23-使用嵌套循环输出乘法口诀表

    1:代码如下: // 3.23.cpp : 定义控制台应用程序的入口点. // #include "stdafx.h" #include <iomanip> #incl ...

  3. 搭建jenkins集群node结点

    配置结点 首先,需要在jenkins的系统设置中新增一个结点 系统管理 -> 节点管理 -> New Node 配置Remote root directory最好和主jenkins的路径一 ...

  4. leetcode 51 N皇后问题

    代码,由全排列转化而来,加上剪枝,整洁的代码: 共有4个变量,res(最终的结果),level,当前合理的解,n皇后的个数,visit,当前列是否放过皇后,由于本来就是在新的行方皇后,又通过visit ...

  5. Jmeter(六)事务

    事务是性能测试之必不可少的关注点, Jmeter默认把每一个请求都统计成了一个事务, 但有时候我们根据业务需求, 会把多个操作统计成一个事务, Jmeter当然也考虑到了这个需求, 因此我们可以通过逻 ...

  6. 阶段3 2.Spring_03.Spring的 IOC 和 DI_5 BeanFactory和ApplicationContext的区别

    核心容器的两个接口.ApplicationContext和BeanFactory 怎么知道对象被创建了呢 我们只需要在实现类里面构造函数内打印输出一段话 然后再这里加上一个断点 运行程序,光标停在这个 ...

  7. Java学习之==>JDBC

    一.概述 官方解释: JDBC(Java DataBase Connectivity,java数据库连接)是一种用于执行SQL语句的 Java API,可以为多种关系型数据库提供统一访问,它由一组用 ...

  8. PC端网页嵌入百度地图

    1 打开百度地图生成器: http://api.map.baidu.com/lbsapi/creatmap/ 2 设置好了之后,点击获取代码,将代码粘贴到文件中保存为html文件 参考网址:https ...

  9. java:LeakFilling(JSP,servlet,Ajax,Json,Path)

    1. request.setAttribute("test", "测试");       request.getRequestDispatcher(" ...

  10. Cocos2d-X多线程(1) 在cocos2d-x中使用多线程

    教科书上说:进程是资源分配的最小单位,线程是CPU调度的最小单位. 进程是程序在计算机上的一次执行活动.直观的讲就是会产生一个pid. int main() {     //业务逻辑代码     re ...