【C语言】静态关键字static的用法(详解)

简介: 不同于其他关键字,他们都有多种用法,而且在一定环境下使用,可以提高程序的运行性能,优化程序的结构。这篇文章主要介绍了C语言中静态关键字static的作用,对大家学习C语言非常有帮助。

【前言】


不同于其他关键字,他们都有多种用法,而且在一定环境下使用,可以提高程序的运行性能,优化程序的结构。这篇文章主要介绍了C语言中静态关键字static的作用,对大家学习C语言非常有帮助。


一、静态关键字static

C语言中,static关键字修饰变量和函数:


1、变量


2、函数


二、static基本用法

被static修饰的变量属于类变量,可以通过类名.变量名直接引用,而不需要new出一个类来

被static修饰的方法属于类方法,可以通过类名.方法名直接引用,而不需要new出一个类来


被static修饰的变量、被static修饰的方法统一属于类的静态资源,是类实例之间共享的,换言之,一处变、处处变。JDK把不同的静态资源放在了不同的类中而不把所有静态资源放在一个类里面,很多人可能想当然认为当然要这么做,但是是否想过为什么要这么做呢?个人认为主要有三个好处:


1.不同的类有自己的静态资源,这可以实现静态资源分类。比如和数学相关的静态资源放在java.lang.Math中,和日历相关的静态资源放在java.util.Calendar中,这样就很清晰了

2.避免重名。不同的类之间有重名的静态变量名、静态方法名也是很正常的,如果所有的都放在一起不可避免的一个问题就是名字重复,这时候怎么办?分类放置就好了。

3.避免静态资源类无限膨胀,这很好理解。


三、static具体用法

1.变量

1.1局部变量

1、用静态关键字static修饰的局部变量,在编译的过程中,会在数据区为该变量开辟空间,并对其进行初始化,如果代码中未对其进行初始化,则系统默认初始化为0。


2、用static修饰的局部变量,会延长局部变量的寿命,超出函数的生存期。


3、对静态关键字修饰的局部变量的初始化。


变量在全局数据区分配内存空间,编译器自动对其初始化

其作用域为局部作用域,当定义它的函数结束时,其作用域随之结束


代码示例:

#include <stdio.h>
void fn(void)
{
    int n = 10;
    printf("n=%d\n", n);
    n++;
    printf("n++=%d\n", n);
}
void fn_static(void)
{
    static int n = 10;
    printf("static n=%d\n", n);
    n++;
    printf("n++=%d\n", n);
}
int main(void)
{
    fn();
    printf("--------------------\n");
    fn_static();
    printf("--------------------\n");
    fn();
    printf("--------------------\n");
    fn_static();
    return 0;
}

代码结果:

n=10
n++=11
--------------------
static n=10
n++=11
--------------------
n=10
n++=11
--------------------
static n=11
n++=12

可见,静态局部变量的效果跟全局变量有一拼,但是位于函数体内部,就极有利于程序的模块化了。


1.2全局变量

全局变量定义在函数体外部,在全局数据区分配存储空间,且编译器会自动对其初始化。


普通全局变量对整个工程可见,其他文件可以使用extern外部声明后直接使用。也就是说其他文件不能再定义一个与其相同名字的变量了(否则编译器会认为它们是同一个变量)。


静态全局变量仅对当前文件可见,其他文件不可访问,其他文件可以定义与其同名的变量,两者互不影响。


在定义不需要与其他文件共享的全局变量时,加上static关键字能够有效地降低程序模块之间的耦合,避免不同文件同名变量的冲突,且不会误使用。


2.函数

函数的使用方式与全局变量类似,在函数的返回类型前加上static,就是静态函数。


其特性如下:

1.静态函数只能在声明它的文件中可见,其他文件不能引用该函数

2.不同的文件可以使用相同名字的静态函数,互不影响


非静态函数可以在另一个文件中直接引用,甚至不必使用extern声明


代码示例:

c4c9103e06f941e4b24cfce2512e59c1.png


dfb6b781b3ad49588d0be122a9b08f9b.png

下面的例子说明使用static声明的函数不能被另一个文件引用:


068c3ea7fad747f48edb699a5f1820e6.png


会发现Add函数无法被解析了,static修饰后Add函数的作用域变小了。


本质和全局变量很像:

1.函数本身也是有外部链接属性的

2.被static修饰后,函数的外部链接属性被修改成内部链接属性,使得这个函数只能在自己的源文件内被使用,因此函数的作用域就变小了


3.面向对象

静态数据成员


在类内数据成员的声明前加上static关键字,该数据成员就是类内的静态数据成员。


其特点如下:


1.静态数据成员存储在全局数据区,静态数据成员在定义时分配存储空间,所以不能在类声明中定义

2.静态数据成员是类的成员,无论定义了多少个类的对象,静态数据成员的拷贝只有一个,且对该类的所有对象可见。也就是说任一对象都可以对静态数据成员进行操作。而对于非静态数据成员,每个对象都有自己的一份拷贝。

3.由于上面的原因,静态数据成员不属于任何对象,在没有类的实例时其作用域就可见,在没有任何对象时,就可以进行操作

4.和普通数据成员一样,静态数据成员也遵从public, protected, private访问规则

5.静态数据成员的初始化格式:<数据类型><类名>::<静态数据成员名>=<值>

6.类的静态数据成员有两种访问方式:<类对象名>.<静态数据成员名> 或 <类类型名>::<静态数据成员名>


同全局变量相比,使用静态数据成员有两个优势:

1.静态数据成员没有进入程序的全局名字空间,因此不存在与程序中其它全局名字冲突的可能性

2.可以实现信息隐藏。静态数据成员可以是private成员,而全局变量不能


静态成员函数

与静态数据成员类似,静态成员函数属于整个类,而不是某一个对象,其特性如下:


1.静态成员函数没有this指针,它无法访问属于类对象的非静态数据成员,也无法访问非静态成员函数,它只能调用其余的静态成员函数

2.出现在类体外的函数定义不能指定关键字static

3.非静态成员函数可以任意地访问静态成员函数和静态数据成员

以上就是关键字static的全部用法,希望对大家灵活运用关键字static有所帮助!

3130aecf142e4659af6fddc911eaba46.png

相关文章
|
2月前
|
算法 编译器 C语言
C语言猜数字小游戏(也包含python实现的用法)
本文基于VS2022、pycharm和前面的知识,写一个凭借分支与循环的小游戏,比如: 写一个猜数字游戏 游戏要求: 电脑自动生成1~100的随机数 玩家猜数字,猜数的过程中,根据猜测数据的大小给出大了或小了的反馈,直到猜对,游戏结束 在pyhton中生成随机数是比较简单的,可以直接导入random的包,直接生成随机数,导致写猜数字小游戏变成了判读语句和循环语句嵌套就能写出来,所以我不做过多的介绍了,可以直接看后面的代码展示,想了解更多的python可看python的基础知识,这里面有我在学习python的过程中写的笔记
31 0
|
10天前
|
Unix Linux 编译器
C语言中EOF的用法
C语言中EOF的用法
7 0
|
10天前
|
安全 编译器 C语言
C语言中的const关键字
C语言中的const关键字
15 2
|
2月前
|
C语言
C语言4🔥:运算符,运算符的基本用法
C语言4🔥:运算符,运算符的基本用法
33 0
|
2月前
|
程序员 C语言
在C语言中,typedef是一种用来创建新的数据类型名的关键字
在C语言中,typedef是一种用来创建新的数据类型名的关键字
10 0
|
2月前
|
存储 编译器 C语言
C语言的关键字
C语言的关键字
14 0
|
2月前
|
存储 编译器 C语言
c语言中的关键字
c语言中的关键字
9 0
|
2月前
|
编译器 程序员 Linux
深入理解C语言中的return关键字与函数返回机制
深入理解C语言中的return关键字与函数返回机制
|
2月前
|
C语言
C语言中关键字static的三种用法
C语言中关键字static的三种用法
|
9月前
|
存储 编译器 C语言
【C语言】关键字static——static修饰局部变量、全局变量和函数详解!
【C语言】关键字static——static修饰局部变量、全局变量和函数详解!
227 0