




已阅读5页,还剩52页未读, 继续免费阅读
版权说明:本文档由用户提供并上传,收益归属内容提供方,若内容存在侵权,请进行举报或认领
文档简介
第8章更上一层楼 C程序的模块结构 8 1结构化程序设计方法8 2合理使用程序中的变量8 3组织多文件模块程序 8 1结构化程序设计方法 8 1 1自顶向下分析问题8 1 2模块化程序设计8 1 3结构化程序编写8 1 4学生成绩统计程序 8 1 1自顶向下分析问题 结构化程序设计结构化程序设计强调程序设计的风格和程序结构的规范化 提倡清晰的结构 其基本思路是把一个复杂问题的求解过程分阶段进行 每个阶段处理的问题都控制在人们容易理解和处理的范围内 自顶向下结构化的程序设计可以把大的复杂的问题分解成小问题 然后各个击破 8 1 1自顶向下分析问题 例如我们要开发一个学生成绩统计程序 其基本要求如下 输入若干学生的5门功课的成绩 分别输出每个学生成绩的平均分 每门功课的平均分 以及最高分所对应的学生和功课 其层次结构如图所示 8 1 1自顶向下分析问题 学生统计成绩程序 成绩输入 数据计算 查找最高分 计算学生的平均分 计算功课的平均分 输出成绩 学生成绩统计程序的层次结构图 8 1 2模块化程序设计 模块化程序设计的主要工作是设计出程序的合理模块构成 一般来说 经过自顶向下方法分解问题 设计出相应的层次结构图 图中每一个方块就可以看作是系统中的一个模块 8 1 2模块化程序设计 模块化程序设计原则模块独立性 即模块间的联系尽量简单模块化程序设计 模块独立性具体体现在 一个模块只完成一个指定的功能 模块之间只存在通过参数进行调用的关系 尽量避免一个模块直接使用另一个模块的内部数据 或者一个模块经goto语句直接进入另一个模块内运行 函数内要尽量使用自动变量 全局变量要慎用 一个模块只有一个入口和一个出口 8 1 2模块化程序设计 学生成绩统计进行如下的模块化设计 设计以下函数 每个完成一项功能 代表一个模块 主函数 main 数据输入 input stu 数据计算 calc data 计算学生平均分 avr stu 计算课程平均分 avr cor 查找最高分 highest 输出成绩 output stu 模块间的调用关系 函数calc data 分别调用函数avr stu 和avr cor 以完成数据计算的功能 而在主函数中 只要依次调用函数input stu calc data highest output stu 即可 8 1 3结构化程序编写 当一个软件经模块化设计后 每一个模块可以独立编程 在第3章曾介绍过 任何只含有一个入口和一个出口的程序 均可由顺序 选择和循环三种结构组成 因此在编程时 应该严格采用三种基本程序结构 C程序提供了丰富的语句来实现这三种程序结构 对于编程者来说 应首先确定适合于三种基本结构的程序流程图 然后使用相应语句 8 1 3结构化程序编写 开始 max score score 0 0 max stu max cor 1 max score score i j max stu i 1 max cor j 1 结束 i 10 j 5 score i j max N N N Y Y Y 函数highest 的程序流程图 假设以二维数组score 10 5 存放学生的成绩信息 变量max score max stu和max cor分别存放最高分及所在的学生编号和课程编号 8 1 3结构化程序编写 实现程序可读性的要求符号的命名程序的注释语句结构良好的交互特性 8 1 3学生成绩统计程序 例8 1学生成绩统计程序 include 定义全局变量和数组 defineM5floatscore 10 M floata stu 10 a cor M intN floatmax score intmax stu max cor 声明子函数 voidinput stu voidcalc data voidavr stu voidavr cor voidhighest voidoutput stu 数组score用于存放10名学生的课程成绩 数组a stu用于存放每名学生的平均分 数组a cor用于存放每门课程的平均分 变量max score用于存放最高分 变量max stu和max cor用于存放最高分所在的学生编号及其课程编号 8 1 3学生成绩统计程序 voidmain 主函数 input stu 调用函数input stu 输入学生各门功课的成绩 calc data 调用函数calc data 进行数据计算 highest 调用函数highest 查找最高分 output stu 调用函数output stu 输出统计信息 voidinput stu 输入学生的成绩 inti j printf 请输入学生人数 10 scanf d 8 1 3学生成绩统计程序 voidcalc data 计算学生的平均分 avr stu 调用函数avr stu 求出每个学生的平均分 avr cor 调用函数avr cor 找出学生成绩中的最高分 voidavr stu 计算学生的平均分 inti j floats for i 0 i N i s 0 for j 0 j M j s s score i j a stu i s M 8 1 3学生成绩统计程序 voidavr cor 计算课程的平均分 inti j floats for j 0 j M j s 0 for i 0 i N i s s score i j a cor j s float N 8 1 3学生成绩统计程序 voidhighest 查找最高分 floathigh inti j max stu max cor 1 high score 0 0 for i 0 ihigh high score i j max stu i 1 max cor j 1 max score high 8 1 3学生成绩统计程序 voidoutput stu 输出统计信息 inti j r c floath printf n序号课程1课程2课程3课程4课程5平均分 for i 0 i N i printf nNO 2d i 1 for j 0 j M j printf 8 2f score i j printf 8 2f a stu i printf n课平均 for j 0 j M j printf 8 2f a cor j printf n最高分 8 2f是 d号学生的第 d门课 n max score max stu max cor 8 1 3学生成绩统计程序 运行结果 请输入学生人数 10 5请输入学生1的5个成绩 7888699096请输入学生2的5个成绩 8185878998请输入学生3的5个成绩 6960787180请输入学生4的5个成绩 7879645866请输入学生5的5个成绩 9997909289 8 1 3学生成绩统计程序 序号课程1课程2课程3课程4课程5平均分NO178 0088 0069 0090 0096 0084 20NO281 0085 0087 0089 0098 0088 00NO369 0060 0078 0071 0080 0071 60NO478 0079 0064 0058 0066 0069 00NO599 0097 0090 0092 0089 0093 40课平均81 0081 8077 6080 0085 80最高分 99 00是5号学生的第1门课 运行结果 8 2合理使用程序中的变量 8 2 1局部变量和全局变量8 2 2变量的生存期和存储类别8 2 3自动变量和寄存器变量8 2 4静态局部变量8 2 5外部变量 8 2 1局部变量和全局变量 局部变量C语言中把定义在函数内部的变量称为局部变量局部变量的有效作用范围局限于所在的函数内部 即只有在所在函数中才能使用它 8 2 1局部变量和全局变量 局部变量 例8 2局部变量的作用范围 includeintsum inta intb nts s a b returns voidmain intx y s scanf d d 在两个函数中都有一个名为s的局部变量 尽管同名 它们其实是两个不同的变量实体 有各自的存储单元和使用范围 不会相互干扰 8 2 1局部变量和全局变量 局部变量 例8 3复合语句中的局部变量 includevoidmain inta a 1 intb 2 b a b a a b printf d a 复合语句中的局部变量 其作用范围被局限于复合语句内 一般用作小范围内的临时变量 8 2 1局部变量和全局变量 全局变量定义在函数外面而不属于任意函数的变量称为全局变量 也称为外部变量或全程变量 全局变量的作用范围是从定义开始到程序所在文件的结束 它对作用范围内所有的函数都起作用 8 2 1局部变量和全局变量 全局变量 例8 4全局变量的作用范围 includeintx 1 定义全局变量x intf inta a a x returna inty 定义全局变量y voidmain intb 3 y f b 全局变量赋值 printf x d y d x y 8 2 1局部变量和全局变量 全局变量 例8 5全局变量与局部变量同名 includeintt 定义全局变量t voidf1 inta intb printf d n a b t 引用全局变量t voidf2 intt 3 定义局部变量t printf d n a b t 引用局部变量t voidmain intx 1 y 2 t 5 全局变量t赋值 f1 x y f2 x y 如果全局变量与局部变量同名 且全局变量的作用范围覆盖局部变量的作用范围时 则在局部变量的作用范围内全局变量被屏蔽 只有局部变量起作用 运行结果 159 8 2 1局部变量和全局变量 全局变量 利用全局变量从函数中得到多个计算结果voidhighest 查找最高分 floathigh inti j max stu max cor 1 high score 0 0 for i 0 ihigh high score i j max stu i 1 max cor j 1 max score high 变量max score max stu和max cor都是在前面已定义的全局变量 由于全局变量的作用范围覆盖全程序 在调用了此函数后 就可以在调用函数中取得这三个全局变量的值 8 2 1局部变量和全局变量 全局变量全局变量使用起来比局部变量自由度大 给编程带来很多的便利过多使用全局变量也会带来副作用 导致各函数间出现相互干扰全局变量是作为一种特殊手段 在特殊情况下用于多个函数之间的数据交流 而一般情况下 应尽量使用局部变量和函数参数传递的方式 8 2 2变量的生存期和存储类别 变量的生存期C程序都是从main函数开始运行的 随着程序流程的执行 程序中的变量从定义开始在内存中被分配存储空间 一直到其所在函数或整个程序运行结束时 变量的存储空间被回收 变量的这个从产生到消亡的过程称为生存期 或称为生命周期 8 2 2变量的生存期和存储类别 变量的生存期 例8 6 includeints 0 intsum intn inti for i 1 i n i s s i voidmain intx scanf d 局部变量x的生存期由main函数决定局部变量n i的生存期由函数sum决定全局变量s 其生存期最长 从整个程序开始直至结束 运行结果 5sum 15 为什么全局变量与局部变量的生存期会不同呢 这是与它们在分配内存空间时所在的存储区域相关的 8 2 2变量的生存期和存储类别 变量的存储类别 程序存储空间示意图 静态数据区中的变量一旦被分配空间 一直到程序执行完毕才会被释放动态数据区中的变量在程序执行过程中是被实时动态分配和释放的 8 2 2变量的生存期和存储类别 变量的存储类别变量的存储类别就是指数据在内存中存储的方式根据变量的存储类别 变量具体可以分为自动变量 寄存器变量 静态变量和外部变量 自动变量存放在动态存储区 静态变量和外部变量存放在静态存储区 根据变量的存储类别 就可以知道变量的作用范围和生存期 8 2 3自动变量和寄存器变量 自动变量函数在被调用之前 其局部变量并未分配相应存储单元 即在内存中是不存在的 只有调用了某函数 其形参和局部变量才被分配相应的存储空间 一旦函数运行结束 返回主调函数后 其定义的所有形参和局部变量将不复存在 相应的存储空间由系统回收 我们把具有这种特性的局部变量称为自动变量 自动变量都是在动态存储区中分配空间的 自动变量的定义形式 auto类型名变量表 auto可以省略 例如 autointx y inta b 以前我们定义的局部变量都是自动变量 8 2 3自动变量和寄存器变量 自动变量 在main 中共调用了3次函数f 因此 自动变量n m有3次从产生到消亡的过程 变量m每次都被重新分配空间并赋初值0 例8 7 includeints 0 intf intn autointm 0 m returnm n voidmain inti for i 1 i 3 i printf d n f i 运行结果 234 8 2 3自动变量和寄存器变量 自动变量 当计算fact 1 时 有4个fact 克隆体同时在运行 虽然名字都为fact 但实体不同 每个fact 都有自己的自动变量x 之间互不干扰 每个变量的作用范围只在所在的函数内 递归函数中的自动变量intfact intx if x 1 return1 elsereturnx fact x 1 fact 4 4 fact 3 3 fact 2 2 fact 1 fact 1 1 8 2 3自动变量和寄存器变量 寄存器变量寄存器变量是把数据存储在计算机CPU 中央处理器 内部的寄存器单元上 其数据存取速度比内存单元快得多 寄存器变量只适用于整形 其定义格式为 registerint变量表 寄存器变量的使用方式与自动变量完全相同 8 2 4静态局部变量 在局部变量定义时 如果在类型名前再加上关键字static 则该局部变量就是静态局部变量静态局部变量存放在静态存储区 不会像自动变量那样因为函数的结束而被系统回收 它的生命周期会持续到程序结束 但它的作用范围仍只限于所在的函数内 8 2 4静态局部变量 示例 例8 8voidf inti staticinta 1 静态变量定义 intb 1 自动变量定义 a a i b b i printf a d b d n a b voidmain intn for n 1 n 3 n f n f 被循环调用 运行结果 a 2 b 2a 4 b 3a 7 b 4 对于静态变量来说 如果定义时没有赋初值 系统将自动赋0 8 2 4静态局部变量 示例 静态局部变量与自动变量的比较 8 2 4静态局部变量 结论静态局部变量的生命周期始于函数的第一次调用 贯穿于整个程序变量作用范围仍然受限于所在的函数内 不能在其它函数中使用静态变量和全局变量一样 属于变量的特殊用法 若没有静态保存的要求 不建议使用静态变量 8 2 5外部变量 用命令extern对全局变量进行声明的变量称为外部变量对于外部变量 其使用有两种情况 一种是在一个程序文件内的全局变量声明 第二种情况是当程序由多个文件构成时的全局变量声明 8 2 5外部变量 示例 例8 9在一个程序文件内声明外部变量 includevoidave floata floatb externaverage 声明average为外部变量 具体定义在后面 voidave floata floatb average a b 2 全局变量赋值 使用先于定义 voidmain floatx y scanf d d 在使用全局变量的后面定义全局变量 8 2 5外部变量 说明外部变量实际上就是扩展了全局变量在程序文件中的作用范围在用extern声明外部变量时 变量的类型名可以写也可以省略 例如 externaverage externfloataverage 外部变量只是起说明作用 告诉C编译器该变量后面会定义 它并不分配内存空间 对应的存储单元仍然在变量定义处分配 多文件模块程序中的外部变量声明将在下一节介绍 8 3组织多文件模块程序 8 3 1文件包含8 3 2全局变量与程序文件模块8 3 3函数与程序文件模块 8 3 1文件包含 一般的一个C程序通常存放在一个C文件中 一个大程序就会由几个C文件组成 每一个文件又可能包含若干个函数 我们把保存有部分程序的文件称为程序文件模块 当一个 语言程序由多个文件模块组成时 整个程序只允许有一个main 函数 程序的运行从main 开始 为了能调用写在其它文件模块中的函数 文件包含是一个有效的解决方法 8 3 1文件包含 文件包含的格式为 include或 include 需包含的文件名 文件包含 include 对我们来说并不是新的内容 以前编写程序时 如果用到输入输出函数数学函数时 需要在程序头写上 include或 include 8 3 1文件包含 文件包含的作用是把指定的文件模块内插入到 include所在的位置 当程序编连接时 系统会把所有 include指定的文件拼接生成可执行代码 当经过连接生成可执行代码后 include便不再存在 因此include不是真正的C语句 它是编译预处理命令 尾号不用分号结束 8 3 1文件包含 文件模块名 F1 clongfact intn inti longres 1 for i 1 i n i res res i returnres 文件模块名 F2 clongsum intn inti longs 0 for i 1 i n i s s i returns 文件模块名 F3 c include F1 c include F2 c voidmain intn scanf d 例8 10用文件包含实现计算n的阶乘与累加和 8 3 2全局变量与程序文件模块 1 外部变量外部变量可以用extern在一个程序文件内声明外部变量 以扩展全局变量的作用范围 外部变量还有另一种应用情况 当程序由多个文件构成时 在一个文件中用extern声明另一个文件中定义的全局变量 全局变量在某一个文件模块中定义一次 其它文件模块如果要使用该全局变量的话 应使用extern在本文件模块中对该全局变量进行外部变量声明 告诉计算机这是一个在另外文件模块中定义的全局变量 当程序连接时会统一指向全局变量定义的文件模块上 8 3 2全局变量与程序文件模块 其中file1 c定义了全局变量PI 而file2 c中的函数也需要使用全局变量PI 因此只要在文件file2 c中用extern将全局变量PI声明成外部变量即可使
温馨提示
- 1. 本站所有资源如无特殊说明,都需要本地电脑安装OFFICE2007和PDF阅读器。图纸软件为CAD,CAXA,PROE,UG,SolidWorks等.压缩文件请下载最新的WinRAR软件解压。
- 2. 本站的文档不包含任何第三方提供的附件图纸等,如果需要附件,请联系上传者。文件的所有权益归上传用户所有。
- 3. 本站RAR压缩包中若带图纸,网页内容里面会有图纸预览,若没有图纸预览就没有图纸。
- 4. 未经权益所有人同意不得将文件中的内容挪作商业或盈利用途。
- 5. 人人文库网仅提供信息存储空间,仅对用户上传内容的表现方式做保护处理,对用户上传分享的文档内容本身不做任何修改或编辑,并不能对任何下载内容负责。
- 6. 下载文件中如有侵权或不适当内容,请与我们联系,我们立即纠正。
- 7. 本站不保证下载资源的准确性、安全性和完整性, 同时也不承担用户因使用这些下载资源对自己和他人造成任何形式的伤害或损失。
评论
0/150
提交评论