c语言中static 用法

待兔 等级 644 0 0

static在c里面可以用来修饰变量,也可以用来修饰函数。 先看用来修饰变量的时候。变量在c里面可分为存在全局数据区、栈和堆里。其实我们平时所说的堆栈是栈而不是堆,不要弄混。

int a ;
int main()
{
    int b ; 
    int c* = (int *)malloc(sizeof(int));
}

a是全局变量,b是栈变量,c是堆变量。 static对全局变量的修饰,可以认为是限制了只能是本文件引用此变量。有的程序是由好多.c文件构成。彼此可以互相引用变量,但加入static修饰之后,只能被本文件中函数引用此变量。 static对栈变量的修饰,可以认为栈变量的生命周期延长到程序执行结束时。一般来说,栈变量的生命周期由OS管理,在退栈的过程中,栈变量的生命也就结束了。但加入static修饰之后,变量已经不再存储在栈中,而是和全局变量一起存储。同时,离开定义它的函数后不能使用,但如再次调用定义它的函数时,它又可继续使用, 而且保存了前次被调用后留下的值。 static对函数的修饰与对全局变量的修饰相似,只能被本文件中的函数调用,而不能被同一程序其它文件中的函数调用。

文件a.c

static int i; //只在a文件中用 int j; //在工程里用 static void init() //只在a文件中用 { } void callme() //在工程中用 { static int sum; }

上面的全局i变量和init()函数只能用在a.c文件中,全局变量sum的作用域只在callme里。变量j和函数callme()的全局限扩充到整个工程文件。所以可以在下面的b.c中用extern关键字调用。extern告诉编译器这个变量或者函数在其他文件里已经被定义了。

文件b.c

extern int j;           //调用a文件里的
extern void callme();   //调用a文件里的
int main()
{
  ...
}

extern的另外用法是当C和C++混合编程时如果c++调用的是c源文件定义的函数或者变量,那么要加extern来告诉编译器用c方式命名函数:

文件A.cpp调用a.c里面的变量i和函数callme()

extern "C"  //在c++文件里调用c文件中的变量
{
   int j;
   void callme();
}
int main()
{
   callme();
}

二 static法则:

  • A、若全局变量仅在单个C文件中访问,则可以将这个变量修改为静态全局变量,以降低模块间的耦合度;
  • B、若全局变量仅由单个函数访问,则可以将这个变量改为该函数的静态局部变量,以降低模块间的耦合度;
  • C、设计和使用访问动态全局变量、静态全局变量、静态局部变量的函数时,需要考虑重入问题;

全局变量有外部、静态两种存储方式。

  • (1)全局变量一般用外部存储方式存储,用保留字extern加以定义。此时,变量的作用域是构成整个程序的所有程序文件,也就是定义的外部变量可供其它程序文件使用。 使用这样的全局变量一定要非常慎重,一旦产生错误,将波及整个程序。
  • (2)如果希望全局变量仅限于本程序文件使用,而其它程序文件中不能引用,这时必须将其存储方式定义为静态存储方式,用保留字static加以定义。此时称为静态外部变量。 例如,在上例文件filel.c中,如果作这样的定义:
static int a:

则变量a的作用域被缩小至本程序文件filel.c,文件file2.c中不能引用。 值得注意的是对全局变量加static,定义为静态存储方式,并不意味着是静态存储;而不加static,是动态存储。两种形式的全局变量(外部变量)都是静态存储方式,都是编译时分配存储空间,但作用域不同。使用静态外部变量,有利于隔离错误,有利于模块化程序设计。 (3)全局变量的缺省存储方式是外部存储方式。 前面章节中的程序没有见到变量的存储类别定义,实际上采用变量的缺省存储方式。对局部变量采用auto方式,对全局变量采用extern方式。这也是至今为止,我们在程序中没有见到auto、extern等的原因。 至此,我们对变量的存储类别及数据类型进行了全面讨论,在此作个小结。

1.变量定义的一般形式

存储类别数据类型变量表;

2.变量定义的作用

①规定了变量的取值范围。 ②规定了变量进行的运行操作。 ③规定了变量的作用域。 ④规定了变量的存储方式。 ⑤规定了变量占用的存储空间。

3.局部变量和全局变量

从作用域角度将变量分为局部变量和全局变量。它们采取的存储类别如下: 局部变量: ①自动变量,即动态局部变量(离开函数,值就消失)。 ②静态局部变量(离开函数,值仍保留)。 ③寄存器变量(离开函数,值就消失)。 ④形式参数可以定义为自动变量或寄存器变量。 全局变量: ①静态外部变量(只限本程序文件使用)。 ②外部变量(即非静态的外部变量,允许其它程序文件引用)。

4.动态存储和静态存储

从变量存在时间可将变量存储分为动态存储和静态存储。静态存储是在整个程序运行时都存在,而动态存储则是在调用函数时临时分配存储单元。 动态存储: ①自动变量(函数内有效)。 ②寄存器变量(函数内有效)。 ③形式参数。 静态存储: ①静态局部变量(函数内有效)。 ②静态外部变量(本程序文件内有效)。 ③外部变量(整个程序可引用)。

5.静态存储区和动态存储区

从变量值存放的位置可将变量存储区分为静态存储区和动态存储区: 内存中静态存储区: ①静态局部变量。 ②静态外部变量。 ③外部变量(可被同一程序其它文件引用)。 内存中动态存储区:自动变量和形式参数。 CPU中的寄存器:寄存器变量。

收藏
评论区

相关推荐

C++概述
概述 C 是静态,可编译,通用,大小写敏感,格式自由的编程语言,它支持程序化,面向对象的,和泛型编程方式。 C 被看作是中间层语言,因为它同时包含了低级语言和高级语言的特性。 C 是于 1979 年在新泽西的茉莉山丘的贝尔实验室由 Bjarne Stroustrup 开发的,它是 C 语言的加强版,最开始它被称作 “C with Classes”,但是
c语言中static 用法
static在c里面可以用来修饰变量,也可以用来修饰函数。 先看用来修饰变量的时候。变量在c里面可分为存在全局数据区、栈和堆里。其实我们平时所说的堆栈是栈而不是堆,不要弄混。 c int a ; int main() { int b ; int c (int )malloc(sizeof(int)); } a是全局变量,b是栈变
计算机专业,如何轻松学习C/C++编程?
C/C 是比其他语言难些,但差距不大。以往很多人说 C/C 难,那是旧时代的产物。那时操作系统(例如 DOS)还没有如今这么强大的功能,像界面设计和底层设计都要靠应用程序来实现。由于 C 的高效率,高端设计大都用 C 语言和汇编语言来写,程序搞得很复杂,初学者有望尘莫及的感觉。C 的简捷表达法比 Fortran, Cobol, Pascal 和 BASIC
C语言_二进制文件
(https://blog.csdn.net/Ustinian_116/article/details/114783972)二进制文件 其实所有文件最终都是二进制的 想想我们之前printf()一个整数的时候
我的C语言基础
C语言32个关键字auto 声明自动变量short 声明短整型变量或函数int 声明整型变量或函数long 声明长整型变量或函数float 声明浮点型变量或函数double 声明双精度变量或函数char 声明字符型变量或函数struct 声明结构体变量或函数union 声明共用数据类型enum 声明枚举类型typedef 用以给数据类型取别名co
C语言入门系列之1.C语言概述和上机运行简单C程序
一、C语言的发展过程C语言是在70年代初问世的。一九七八年由美国电话电报公司(AT&T)贝尔实验室正式发表了C语言,同时由B.W.Kernighan和D.M.Ritchit合著了著名的《THE C PROGRAMMING LANGUAGE》一书 ,通常简称为《K&R》,也有人称之为 《K&R》标准。但是,在《K&R》中并没有定义一个完整的C语言标
C语言入门系列之3.顺序程序设计和输入输出
从程序流程的角度来看,程序可以分为三种基本结构,即顺序结构、分支结构、循环结构,这三种基本结构可以组成各种复杂程序,C语言提供了多种语句来实现这些程序结构。同时C语言提供的输入输出的函数为IO提供了方便的工具。 一、C语句介绍 1.C基本语句C程序的执行部分是由语句组成的,程序的功能也是由执行语句实现的。C语句可分为以下五类: 表达式语句表达式语句:
C语言基础习题50例(二)6-10
给大家推荐一门大数据Spark入门课程,希望大家喜欢。 习题6 用 号输出字母C的图案。实现思路:单行打印即可。代码如下:cinclude <stdio.h int main (void){ printf("\n"); printf("\n"); printf("\n"); printf("
C语言基础习题50例(三)11-15
你们看出神马了吗(\\^_\^\) 习题11 有一对兔子,从出生后第 3 个月起每个月都生一对兔子,小兔子长到第三个月后每个月又生一对兔子,假如兔子都不死,问每个月的兔子总数为多少实现思路:从第1个月起,兔子对数分别为1、1、2、3、5、8、13、21...,显然是斐波拉契数列。代码如下:cinclude<stdio.hint mai
C语言基础习题50例(四)16-20
给大家介绍一堂Python入门课,感觉还不错,适合初学者入门。 习题16 输入两个正整数 m 和 n ,求其最大公约数和最小公倍数。实现思路:求两个数的最大公约数分别采用辗转相除法、辗转相减法、枚举法得到,最小公倍数用两个数之积除以最大公约数即可获得。方式一——辗转相除法:思路:(1)将两整数求余 a%b x;(2)如果x 0;则b为最大公
C语言基础习题50例(七)31-35
喜提头条号黄V,有兴趣的朋友可以关注一波,主写IT领域。 习题31 请输入星期几的第一个字母来判断一下是星期几,如果第一个字母一样,则继续判断第二个字母。实现思路:使用switch语句,如果第1个字母一样,则判断用情况语句或if语句判断第2个字母。也可以使用条件判断语句,实现相近。代码如下:cinclude<stdio.hint ma
C语言基础习题50例(九)41-45
习题41 学习static定义静态变量的用法。实现思路:用static声明和未用static声明变量进行对比,即可得出static的作用。代码如下:cinclude <stdio.h int main(){ void func(); int i; for(i 0;i < 10; i){ func(); } return
C语言基础习题50例(十)46-50
知足常足,终身不辱。月圆缺,水满溢,事情到了极致一定会遭受祸患,只有懂得知足,才是富足。 习题46 宏define命令练习。实现思路:宏通过define命令定义,分为无参宏和带参宏,可以分别进行测试。这只是一种简单的字符串代换。代码如下:cinclude <stdio.hdefine TRUE 1define FALSE 0
dll导出函数
导出函数的概念为什么要导出函数,导出来用来干什么? 前面我们说过,初识DLL,当我们执行某一个程序的时候,相应的dll文件会被调用,一个程序可以调用多个dll,一个dll也可以被多个应用程序调用那么它是调用了全部的东西吗,还是调用了内部一些不为人知的东西举一个例子:你去便利店买水果,你和售货员说,你要买下整个便利店,那么她还以为你是个神经病,肯定不会卖,你要
使用Java 语言编写一个贪吃蛇游戏
使用 Java 语言编写一个贪吃蛇游戏,代码如下:GreedSnake .java package jzjsfx;public class GreedSnake public static void main(String[] args) SnakeModel model new SnakeModel(20, 30); SnakeControl c