《C和指针》笔记14: 作用域和存储类型总结(例子说明)
文章目录
- 题目
 - 答案
 - 解释
 - 总结
 
本文是作用域和存储类型的总结,以一个例子来说明,如果不看解释可以很直接地回答每一条语句的作用域和存储类型,那么说明已经很熟练地掌握这个知识点了。
关于作用域和存储类型可以参考我前面的博客:
《C和指针》笔记10:作用域
 《C和指针》笔记12: 存储类型(自动变量、静态变量和寄存器变量)
题目
请看下面的代码,回答每一行的标识符的链接属性、存储类型和作用域
 
答案
| 行数 | 标识符 | 链接属性 | 存储类型 | 作用域 | 
|---|---|---|---|---|
| 1 | a | external | 静态存储 | 第1-第12行,第17-第29行 | 
| 2 | b | external | 静态存储 | 第2-第6行,第25-第29行 | 
| 3 | c | internal | 静态存储 | 第3-第29行 | 
| 4 | d | external | 静态存储 | 第4行-文件结束 | 
| 4 | e | external | 自动存储 | 第6-11行,第17-19行以及第23-24行 | 
| 6 | f | 不具有链接属性 | 自动存储 | 至函数结束 | 
| 7 | b | 不具有链接属性 | 寄存器存储 | 至函数结束 | 
| 8 | g | 不具有链接属性 | 静态存储 | 至函数结束 | 
| 9 | a | external | 静态存储 | 和第一行的a一样 | 
| 12 | e | 不具有链接属性 | 自动存储 | 延伸至16行 | 
| 13 | g | 不具有链接属性 | 自动存储 | 延伸至16行 | 
| 14 | h | external | 静态存储 | 当前的代码块 | 
| 19 | x | 不具有链接属性 | 自动存储 | 当前的代码块 | 
| 20 | e | 不具有链接属性 | 自动存储 | 当前的代码块 | 
| 25 | i | internal | 静态存储 | 从它声明的位置直到这个源文件结束 | 
解释
- 第1行的a 
- 链接属性: 
external,因为它属于文件作用域的声明在缺省情况下为external链接属性,可以被其他源文件访问。 - 存储类型:静态存储。
 - 作用域:第1-第12行,第17-第29行。静态变量在程序执行之前创建,并一直保持它们的值,直到程序结束。当程序开始执行时,变量a将初始化为5。其作用域应一直延伸到这个源文件结束为止。但是第13行出现的a的局部变量将隐藏同名的静态变量。
 
 - 链接属性: 
 - 第2行的b 
- 链接属性: 
external,如果b的定义在其他地方,第2行的extern关键字在技术上并非必需,但在风格上却是加上这个关键字为好,可以被其他源文件访问。 - 存储类型:静态存储。
 - 作用域:第2-第6行,第25-第29行。静态变量在程序执行之前创建,并一直保持它们的值,直到程序结束。其作用域应一直延伸到这个源文件结束为止。 但是由于第7行出现的b的局部变量将隐藏同名的静态变量。
 
 - 链接属性: 
 - 第3行的c 
- 链接属性: 
internal。static关键字修改了c的缺省链接属性,把它改为internal。只能被当前的源文件访问。 - 存储类型:静态存储。
 - 作用域:第3-第29行。静态变量在程序执行之前创建,并一直保持它们的值,直到程序结束。其作用域应一直延伸到这个源文件结束为止。
 
 - 链接属性: 
 - 第4行的d 
- 链接属性: 
external。作为函数名,d在缺省情况下具有external链接属性,所以其他源文件只要在文件上存在d的原型 ,就可以调用d。函数d的定义对于这个源文件中任何以后想要调用它的函数而言起到了函数原型的作用,如果我们将函数声明为static,就可以把它的链接属性从external改为internal,但这样做将使其他源文件不能访问这个函数。 - 存储类型:静态存储。对于函数而言,存储类型并不是问题,因为代码总是存储于静态内存中。
 - 作用域:第4行直到文件结束。静态变量在程序执行之前创建,并一直保持它们的值,直到程序结束。其作用域应一直延伸到这个源文件结束为止。
 
 - 链接属性: 
 - 第4行的e 
- 链接属性: 不具有链接属性,所以我们只能从函数内部通过名字访问它。
 - 存储类型:自动存储。在函数被调用时被创建,当函数返回时消失。
 - 作用域:第6-11行,第17-19行以及第23-24行。与局部变量冲突导致了作用域的变化。
 
 - 第6行-第8行的f,b,g 
- 链接属性: 不具有链接属性,所以它们不能在函数的外部通过名字访问(这是它们称为局部变量的原因)
 - 存储类型: 
- f是自动存储,当函数每次被调用时,它通过隐式赋值被初始化为15。
 - b是寄存器存储,所以它的初始值是垃圾。
 - g是静态存储,在程序的整个执行过程中一直存在。当函数每次被调用时,它并不会被重新初始化。
 
 - 作用域:到函数结束为止。由于与局部变量冲突,它的作用域限于。
 
 - 第9行的a 
- 它的声明并不需要。这个代码块位于第1行声明的作用域之内。所以它和第一行的a的连接属性、存储类型都是一样的。
 
 - 第12行的-第13行的e,a 
- 链接属性: 不具有链接属性,和先前声明的a和e不同,在这个代码块中,以前声明的同名变量是不能被访问的。
 - 存储类型:自动存储
 - 作用域:延伸至第16行。
 
 - 第14行的h 
- 链接属性: 
external。相当一个全局变量。这是唯一一个必须使用extern关键字的声明,如果没有它,h将变成另一个局部变量。 - 存储类型:静态存储
 - 作用域:当前的代码块。
 
 - 链接属性: 
 - 第19和20行的x,e 
- 链接属性: 不具有链接属性,和先前声明的a和e不同,在这个代码块中,以前声明的同名变量是不能被访问的。
 - 存储类型:自动存储
 - 作用域:当前的代码块。
 
 
这里的e和第4行函数的形参e是不同的变量,它和第12行声明的e也不相同。在这个代码块中,从第11行到第18行并无嵌套,所以编译器可以使用相同的内存来存储两个代码块中不同的变量e。如果想让这两个代码块中的e表示同一个变量,那么你就不应该把它声明为局部变量。
- 第25行的i 
- 链接属性: 
internal,该属性可以防止它被这个源文件之外的任何函数调用。其他的源文件也可能声明它自己的函数i,但它与这个源文件的i是不同的函数。 - 存储类型:静态存储
 - 作用域:从它声明的位置直到这个源文件结束。
 
 - 链接属性: 
 
函数d不可以调用函数i,因为在d之前不存在i的原型。
总结
具有external链接属性的实体在其他语言的术语里称为全局(global)实体,所有源文件中的所有函数均可以访问它。只要变量并非声明于代码块或函数定义内部,它在缺省情况下的链接属性即为external。如果一个变量声明于代码块内部,在它前面添加extern关键字将使它所引用的是全局变量而非局部变量。除了实体的具体定义位置之外,在它的其他声明位置都使用extern关键字。
具有external链接属性的实体总是具有静态存储类型。全局变量在程序开始执行前创建,并在程序整个执行过程中始终存在。从属于函数的局部变量在函数开始执行时创建,在函数执行完毕后销毁,但用于执行函数的机器指令在程序的生命期内一直存在。
局部变量由函数内部使用,不能被其他函数通过名字引用。它在缺省情况下的存储类型为自动,这是基于两个原因:
- 当这些变量需要时才为它们分配存储,这样可以减少内存的总需求量。
 - 在堆栈上为它们分配存储可以有效地实现递归。
 
如果觉得让变量的值在函数的多次调用中始终保持原先的值非常重要的话,可以修改它的存储类型,把它从自动变量改为静态变量。
| 变量类型 | 声明的位置 | 是否存在于堆栈 | 作用域 | 如果声明为static | 
|---|---|---|---|---|
| 全局 | 所有代码块之外 | 否 | 从声明处到文件尾 | 不允许从其他源文件访问 | 
| 局部 | 代码块起始处 | 是 | 整个代码块 | 变量不存储于堆栈中,它的值在程序整个执行器一直保持 | 
| 形式参数 | 函数头部 | 是 | 整个函数 | 不允许 | 
参考
- 《C与指针》
 
相关文章:
《C和指针》笔记14: 作用域和存储类型总结(例子说明)
文章目录 题目答案解释总结 本文是作用域和存储类型的总结,以一个例子来说明,如果不看解释可以很直接地回答每一条语句的作用域和存储类型,那么说明已经很熟练地掌握这个知识点了。 关于作用域和存储类型可以参考我前面的博客: …...
Linux之系统操作参数详解
Linux之系统操作参数详解 date //显示当前日期 日期格式化 %Y year年 %y 年份(以00-99来表示) %j 该年中的第几天 %m month月 (01…12) %w 该周的天数,0代表周日,1代表周一 %D 日期(含年月日) %d day of month (e.g., 01) %T 时间(含时分秒࿰…...
datax 使用
环境准备 List itemLinuxJDK(1.8以上,推荐1.8)Python(2或3都可以)Apache Maven 3.x (Compile DataX) 下载 wget https://datax-opensource.oss-cn-hangzhou.aliyuncs.com/202308/datax.tar.gz建立datax 用户 useradd datax ; echo "datax" | passwd -…...
【C/C++】#define宏替换高级用法
创作不易,本篇文章如果帮助到了你,还请点赞 关注支持一下♡>𖥦<)!! 主页专栏有更多知识,如有疑问欢迎大家指正讨论,共同进步! 🔥c系列专栏:C/C零基础到精通 🔥 给大…...
Android 之 传感器专题 (4) —— 其他传感器了解
本节引言: 在上一节的结尾说了,传感器部分因为笔者没怎么玩过,本节就简单的把剩下的几个常用的 传感器介绍一遍,当作科普,以后用到再慢慢研究~ 1.磁场传感器(Magnetic field sensor) 作用:该传感器主要用…...
【高级搜索】双向广搜,A*,IDDFS,IDA *算法总结 (terse版)
一、双向广搜  双向广搜就是从起点和终点同时往中间搜的一个算法。  注意事项:  在搜索过程中,同一层次下的顺序应该为:搜完一边所有的当前深度的子节点,在搜索另一边。  队列使用  (1)合用…...
CATIA Composer R2023安装教程
软件下载 软件:CATIA Composer版本:2023语言:简体中文大小:1.82G安装环境:Win11/Win10/Win8/Win7硬件要求:CPU2.60GHz 内存8G(或更高)下载通道①百度网盘丨64位下载链接:https://pa…...
git,修改远程分支名称
获取所有远程分支 git branch -r删除远程指定分支 git push --delete origin 测试添加新页面提交新命名本地分支 git push origin 新分支本地分支和远程分支关联 git branch --set-upstream-to origin/远程分支...
信息系统项目管理师(第四版)教材精读思维导图-第六章项目管理理论
请参阅我的另一篇文章,综合介绍软考高项: 信息系统项目管理师(软考高项)备考总结_计算机技术与软件专业技术_铭记北宸的博客-CSDN博客 本章思维导图PDF格式 本章思维导图XMind源文件 目录 6.1 PMBOK的发展 6.2 项目基本要素 6.3…...
[Android]JNI的基础知识
目录 1.什么是JNI 2.配置JNI开发环境NDK 3.创建Native C类型的项目 4. 了解CMakeLists.txt 文件 5.了解native-lib.cpp 文件 6.在 Android 的 MainActivity 中调用 native-lib.cpp 中实现的本地方法 1.什么是JNI JNI(Java Native Interface)是一…...
力扣-哈希-字母异位词分组
题目 给你一个字符串数组,请你将 字母异位词 组合在一起。可以按任意顺序返回结果列表。 字母异位词 是由重新排列源单词的所有字母得到的一个新单词。 示例 1: 输入: strs ["eat", "tea", "tan", "ate", "nat&q…...
excel 分组排序
excel中会遇到对不同分组数据进行排序,比如对于不同班级里的学生按照分数高低进行升序排序,可以采用如下公式 SUMPRODUCT((A$2:A$12A2)*(C$2:C$12>C2))1 如果需要 进行降序排序,将公式中的大于号替换为小于号即可...
vue三级市区联动
默认返回值格式:all:code、name都返回 name:只返回name code:只返回code,level:可设置显示层级 1: 省 2: 省、市 3: 省、市、区 v-model 默认值 可以是 name: [ "天津市", "天津市",…...
C++ 组合类
所谓组合类便是一个类中含有其他类的对象: #include <iostream> #include <string.h> using namespace std;class dog { public:dog() {}dog(const char *n, int age, const char *v) : age(age){strcpy(this->name, n);strcpy(this->var, v);}// 显示这条狗…...
HTML总结2 [转]
以下转载和参考自:HTML 表单。 1、表格 可以通过 CSS 设置表格的样式: 如下为将上面table.lamp th,td样式中的padding注释掉,开启table.lamp中的padding的效果: 2、列表 3、导航栏 导航栏使用<ul>列表实现,…...
【LeetCode-中等题】2. 两数相加
文章目录 题目方法一:借助一个进制位,以及更新尾结点方法一改进:相比较第一种,给head一个临时头节点(开始节点),最后返回的时候返回head.next,这样可以省去第一次的判断 题目 方法一…...
postman接口参数化设置
为什么需要参数化? 我们在做接口测试的过程中,会遇到需要测试同一个接口使用不同的数据的情况,如果每次去一个个填写数据就太麻烦了,这时我们就需要用到接口参数化,我们把数据单独的存放在一个文件中管理,…...
easyexcel poi根据模板导出Excel
1.导入依赖 <!-- poi依赖--> <dependency><groupId>org.apache.poi</groupId><artifactId>poi</artifactId><version>4.0.1</version> </dependency> <!-- poi对于excel 2007的支持依赖--> <dependency…...
怎么把pdf图片转换成jpg?pdf转jpg的方法分享
pdf文件在我们的日常工作中非常的常见,因为这种文件安全性高,不会轻易的乱码,所以受到了我们的欢迎,但是它不容易被编辑,而且占用内存会比较大,所以我们需要将pdf文件进行转换,接下来小编会为大…...
MongoDB 双机热备那篇文章是 “毒”
开头还是介绍一下群,如果感兴趣polardb ,mongodb ,mysql ,postgresql ,redis ,Oracle ,Oceanbase 等有问题,有需求都可以加群群内有各大数据库行业大咖,CTO,可以解决你的问题。加群请加微信号 liuaustin3 (…...
stm32G473的flash模式是单bank还是双bank?
今天突然有人stm32G473的flash模式是单bank还是双bank?由于时间太久,我真忘记了。搜搜发现,还真有人和我一样。见下面的链接:https://shequ.stmicroelectronics.cn/forum.php?modviewthread&tid644563 根据STM32G4系列参考手…...
docker详细操作--未完待续
docker介绍 docker官网: Docker:加速容器应用程序开发 harbor官网:Harbor - Harbor 中文 使用docker加速器: Docker镜像极速下载服务 - 毫秒镜像 是什么 Docker 是一种开源的容器化平台,用于将应用程序及其依赖项(如库、运行时环…...
利用ngx_stream_return_module构建简易 TCP/UDP 响应网关
一、模块概述 ngx_stream_return_module 提供了一个极简的指令: return <value>;在收到客户端连接后,立即将 <value> 写回并关闭连接。<value> 支持内嵌文本和内置变量(如 $time_iso8601、$remote_addr 等)&a…...
ip子接口配置及删除
配置永久生效的子接口,2个IP 都可以登录你这一台服务器。重启不失效。 永久的 [应用] vi /etc/sysconfig/network-scripts/ifcfg-eth0修改文件内内容 TYPE"Ethernet" BOOTPROTO"none" NAME"eth0" DEVICE"eth0" ONBOOT&q…...
html css js网页制作成品——HTML+CSS榴莲商城网页设计(4页)附源码
目录 一、👨🎓网站题目 二、✍️网站描述 三、📚网站介绍 四、🌐网站效果 五、🪓 代码实现 🧱HTML 六、🥇 如何让学习不再盲目 七、🎁更多干货 一、👨…...
Qemu arm操作系统开发环境
使用qemu虚拟arm硬件比较合适。 步骤如下: 安装qemu apt install qemu-system安装aarch64-none-elf-gcc 需要手动下载,下载地址:https://developer.arm.com/-/media/Files/downloads/gnu/13.2.rel1/binrel/arm-gnu-toolchain-13.2.rel1-x…...
Python 实现 Web 静态服务器(HTTP 协议)
目录 一、在本地启动 HTTP 服务器1. Windows 下安装 node.js1)下载安装包2)配置环境变量3)安装镜像4)node.js 的常用命令 2. 安装 http-server 服务3. 使用 http-server 开启服务1)使用 http-server2)详解 …...
在 Spring Boot 项目里,MYSQL中json类型字段使用
前言: 因为程序特殊需求导致,需要mysql数据库存储json类型数据,因此记录一下使用流程 1.java实体中新增字段 private List<User> users 2.增加mybatis-plus注解 TableField(typeHandler FastjsonTypeHandler.class) private Lis…...
SpringAI实战:ChatModel智能对话全解
一、引言:Spring AI 与 Chat Model 的核心价值 🚀 在 Java 生态中集成大模型能力,Spring AI 提供了高效的解决方案 🤖。其中 Chat Model 作为核心交互组件,通过标准化接口简化了与大语言模型(LLM࿰…...
API网关Kong的鉴权与限流:高并发场景下的核心实践
🔥「炎码工坊」技术弹药已装填! 点击关注 → 解锁工业级干货【工具实测|项目避坑|源码燃烧指南】 引言 在微服务架构中,API网关承担着流量调度、安全防护和协议转换的核心职责。作为云原生时代的代表性网关,Kong凭借其插件化架构…...
