c语言中的连接属性,extern与static

在《c和指针》第三章提到连接属性有三种,external,internal,none

在函数内定义的变量都是none连接属性,这个用到的很少,不具体介绍。

external与internal连接属性都是用来描述全局变量以及全局函数的。下面详细介绍这两种连接属性:

(1)external连接属性,也叫外部连接属性。

  我们一般定义的全局变量,如果前面没有加入static关键字,那么这个全局变量的连接属性就是external的,请注意在定义全局变量时请在源文件中定义,也就是在.c文件总定义,声明时在头文件中进行声明。

虽然我们可以在头文件(.h文件)中定义全局变量,但是这样会引入一些不好的bug。具体会引入什么错误,我们下面会详细讲。

  external连接属性的全局变量以及函数的含义就是,在一个文件中定义的external连接属性的全局变量以及函数在另一个文件中也可以访问。

例子1

1 //a.c
2 
3 int a=10;//定义全局变量a,其连接属性是external
4 
5 void print(){
6    
7 }
 1 //main.c
 2 
 3 #include<stdio.h>
 4 extern int a;//因为要调用a.c定义的变量,因此在此处进行声明
 5 extern void print();//因为要调用在a.c定义的函数,在此处声明
 6 
 7 int main(){
 8 
 9   printf("a=%d\n",a); //打印在a.c定义的变量的值
10   print(); //调用在a.c定义的函数
11   return 0;
12 
13 }

上述代码是可以正确运行的。

 

 

  如果全局变量的定义放在头文件中,也就是.h文件中,如果要在另外一个文件中对定义在头文件中的external连接属性的变量进行访问,

不能通过extern关键字仅仅在源文件中进行声明,需要把头文件用include命令包含进源文件。

例子2

1 //a.h
2 
3 int a=20;//在头文件a.h中定义一个全局external连接属性的变量
4 
5 void print(){
6 
7 }

 

//main.c源文件

#include<stdio.h>

//仅仅在源文件中进行了声明,并未把a.h这个头文件包含进来
extern int a;
extern void print();

int main(){

  printf("a=%d\n",a);  
  print();
  return 0;
}

上述代码在连接时会出现错误,错误如图

当我们把a.h头文件包含进main.c源文件时,便可以顺利执行了。

 

  正如上面所说的,extern int a;这是一个声明,如果整个工程的别的地方没有int a;语句,extern int a;这条语句就是变量的定义。在例子1中,在头文件a.c中 

int a=10;就是对变量a进行定义,在main.c中的extern int  a;是对变量a进行声明,如果在a.c中没有int a=10;,那么在main.c中的extern int a;便变成了变量a的定义。

请注意:如果在a.c中定义了int a=10;,在main.c中的声明是extern int a=12;那么再编译时就会出现错我,因为extern int a=12此时不再是变量的声明,

而是变量的定义,那么这时在连接时就会出现重复定义的语法错误。

 

(2)internal连接属性,也叫内部连接

在全局变量以及函数中定义中加上static,那么变量和函数就变成了内部变量与内部函数,意思就是这种内部连接属性的变量和函数只能在当前文件中被访问,

不能被别的文件里面的函数访问。

 

在内部连接属性中需要注意的一点就是,如果某一个全局变量或者函数只需要在当前的文件中进行访问,不需要再别的源文件中进行访问。那么这种函数与全局变量一定不能在头文件中进行定义,如果一个内部变量在头文件a.h中进行了定义,那么任何一个包含a.h头文件的源文件都可以访问这个变量,那么内部变量的意义就不存在了

posted @ 2017-04-30 19:59  阿瞒123  阅读(508)  评论(0)    收藏  举报