内部连接和外部连接C和C++

C++的内部连接和外部连接

转自 :https://blog.youkuaiyun.com/xiexievv/article/details/8491494

当一个实现文件(.cpp …)编译时,预处理器(CPP)首先递归的包含头文件,形成一个保含有所有必要信息的单个源文件. 这个源文件称为 编译单元(translation unit).

内部连接 如果一个名称对于它的编译单元来说是局部的, 并且在连接的时候不可能与其它编译单元中的同样的名称相冲突,则这个名称具有内部连接.即具有内部连接的名称不会被带到目标文件中.

外部连接 在一个多文件程序中,如果一个名称在连接时可以和其他编译单元交互,那么这个名称就具有外部连接. 即具有外部连接的名称会引入到目标文件中,由连接程序进行处理.这种符号在整个程序中必须是惟一的.

具有内部连接的定义包括:

  • 加 static 前缀的全局变量定义.如: static int x;
  • 枚举类型的定义.如: enum Boolean {NO,YES };
  • 类的定义. 如: class Point { int d_x; int d_y; … };
  • 内联函数的定义.如: inline int operator==(const Point& left,const Point&right) { … }
  • union的定义.
  • 名字空间中const常量定义

具有外部连接的定义包括:

  • 非内联的类成员函数.如: Point& Point::operator+=(const Point& right) { … }
  • 非内联,非静态的自由函数. 如: Point operator+(const Point& left, const Point& right) { … }
  • 非静态的全局定义.

声明的内部连接和外部连接

声明本身不会将任何符合引入目标文件,所以声明都是内部连接的.

某些声明可以激活对一个外部连接定义的访问,也许我们会很随便的说这些声明具有外部连接,如:

      int f(); 
      extern int i; 
      class Point { static int s_numPoints; ... }; /* 类静态数据成员声明具有外部连接, 该数据必须在另一个地方被定义,如:   point.c文件的int Point::s_numPoints; */

还有一些声明即不把什么符号引入目标文件,也不能用来激活对外部连接定义的访问,我们常常称这类声明具有内部连接,

      typedef int INT; 
      class Point; 
      struct Point;

把一个带有外部连接的定义放在 .h 文件中都会引起错误.由于类的声明和定义都是内部连接的,一般都放在 .h 文件中.

另外,在C中,const变量是外部连接,C++中,const变量是内部连接

我的理解

  1. 内部连接可以在多个.cpp中定义,互不影响
  2. 外部连接不能在多个.cpp中定义,报编译错误
  3. 有的内部连接可以用extern在其他源文件中访问,有的不能
static void foo()  // 不能
constexpr int goo() // 可以 extern constexpr int goo();
inline int soo() // 不能
  1. 外部连接的定义,定义在cpp文件,extern的声明在h文件,这样可以方便其它文件include。

例如:

int c = 0; // c.cpp文件
extern int c; // c.h 文件
#include "c.h" // 其它用到c的文件

C++内部连接定义

static int a = 1; // static变量
const int b = 1; // 常量
enum Coolean {NO, YES}; // 枚举定义
static void foo() // static 函数
{
}
inline void goo() {} // inline函数
constexpr int soo() {return 1;} // constexpr函数本身就是inline的
class Point //类的定义
{
public:
	Point() {};
	~Point() {};
}
inline Point::aInline() {}; //类的内连等满足上述条件的类的成员函数

C++外部连接的定义

int a = 1; // 非static、非const/constexpr 的全局变量
void foo() {} // 非static、非inline、非constexpr的自由函数
void Point::setX() {} // 类的其它函数

C的连接有三种

转自:https://docs.microsoft.com/en-us/cpp/c-language/internal-linkage?view=msvc-170

内部连接

static的全局、局部对象(object)
static的函数
(因此,C的所有const常量是外部连接)

外部连接

文件级别的函数声明,有extern
文件级别的对象(object)声明

无连接

代码块级别声明的标识符,且没有extern。
除了对象和函数之外的标识符

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值