【C++】009、extern关键字

一、extern关键字设计的目的只有一个:那就是跨文件、跨语言地正确找到符号

  • 作为外部声明,告诉编译器变量或函数在别的文件里有定义,让编译器去别的目标文件找查看,先别急着报错。

  • 配合C语言使用(extern "C"),用于禁止C++的符号修饰(Name Mangling)功能,实现C和C++的混合编程

二、extern的基础使用

修饰变量或函数,只做声明,不定义

  • 本质:extern 关键字修饰的声明是承诺,而不是定义,它不分配内存,只是告诉编译器,这个符号(变量/函数)在其他编译单元(.cpp文件)中有定义,请链接时去哪里找。

  • 代码实现

cpp 复制代码
// FileA.cpp
int g_counter = 0;          // 定义(分配内存)
void logMessage() { ... }   // 定义

// FileB.cpp
extern int g_counter;       // 声明(不分配内存),告诉编译器去外部找
extern void logMessage();   // 声明(通常省略,函数默认就是extern的)

void test() {
    g_counter++;            // 链接时去 FileA.obj 找 g_counter
    logMessage();           // 链接时去 FileA.obj 找 logMessage
}

三、extern "C"的底层原理与使用场景

1、为什么需要设计出extern "C"?

  • 一句话总结:为了让C++兼容C,实现在C++程序中调用C语言函数库

  • C语言:符号名就是函数名,比如 void foo(int) 他的符号名就是 foo (注意C语言没有函数重载)

  • C++:支持函数重载,编译器会进行名字修饰,void foo(int) 会被修饰为 _Z3fooi, 在修饰后的符号名会标记参数信息

使用冲突:

  • 如果C++程序要调用一个C语言的库(.so, .a),默认链接时会去找 _Z3fooi,但C语言的库中只有foo,肯定找不到,会报链接错误(Undefined Reference)

2、extern "C"的标准写法

1)直接包裹单个函数

  • 在C++程序中调用C语言函数
cpp 复制代码
extern "C" {
    void c_function(int x);   // 告诉编译器:按 C 的规则去找这个函数
    int c_global_var;
}

2)兼容C/C++两种语言的双编译的头文件中调用extern

  • 既能让C++编译器识别,也能让C编译器识别

  • __cplusplus是C++编译器内置的宏

cpp 复制代码
// my_module.h
#ifdef __cplusplus
extern "C" {
#endif

// 这里是 C 语言接口声明(结构体、函数原型)
void init_module();
void process_data(int* data, int len);

#ifdef __cplusplus
}
#endif

3、类成员不能使用extern "C"

  • extern "C"只能修饰全局函数和全局变量

  • 不能作用域类成员函数,因为成员函数this指针和虚表(vtable),而C语言没有这两个概念

相关推荐
jiay26 小时前
【.net10】顶级程序语句
java·开发语言
淼澄研学7 小时前
Python进阶实战:深入解析推导式与生成器等5大核心特性
开发语言·python
2601_953824617 小时前
【计算机毕业设计】基于Spring Boot的画师接稿平台设计与实现
java·spring boot·后端
小宋10218 小时前
不用学算法也能玩转 AI?普通 Java 程序员转 AI 应用开发路线
java·人工智能·重构
米码收割机8 小时前
【Python】Django 电子设备商城系统(源码+说明文档)[独一无二]
开发语言·python·django
互联网中的一颗神经元8 小时前
小白python入门 - 38. 动态内容:接口优先与自动化扫盲
开发语言·python·自动化
我是唐青枫8 小时前
Java Jetty 实战详解:从嵌入式 HTTP 服务到 Spring Boot 容器替换
java
带刺的坐椅8 小时前
当所有人都在用 TS/Python 写 Agent,我们为什么坚持 Java
java·ai·solon·codex·opencode·soloncode
黑客-秋凌8 小时前
使用Python+selenium实现第一个自动化测试脚本
开发语言·自动化测试·软件测试·python·selenium·测试工具
小王师傅668 小时前
英语学习记
java·学习