[工学]C语言程序设计_06章 循环结构程序设计_图文

发布于:2021-04-21 14:34:46

第六章 循环结构程序设计
6.1 概述
循环结构主要有:
(1)用goto语句和if语句构成循环; (2)用while语句;

(3)用do-while语句;
(4)用for语句。

1

6.2 goto语句以及用goto语句构成循环
goto语句为无条件转向语句,它的一般形式为: goto 语句标号;
(1)语句标号用标识符表示。标识符的命名规则和变量名相 同,即由字母、数字和下划线组成,其第一个字符必 须为字母或下划线,不能用整数来作标号; (2)goto语句通常有两种用途: 1. 与if语句一起构成循环结构; 2. 从循环体中跳转到循环体外; (3)goto语句的使用不符合结构化程序的原则,一般尽量不 用,除非万不得已。
2

例6.1 用if语句和goto语句构成循环,求

?n
n ?1

100

main( ) { int i,sum=0; i=1; loop: if(i<=100) { sum=sum+i; i++; goto loop; } printf(“%d”,sum); }

3

6.3 while语句
一般形式: while(表达式) 内嵌语句 特点:先判断表达式,当它为真(非0 )时,再执行内嵌语 句;若为假(0),则不执行内嵌语句。这样的循环 结构我们称为“当型”循环结构。 流程图: 表达式 非0 内嵌语句 0

4

例6.2 求 ? n n ?1 main( ) { int i,sum=0; i=1; while (i<=100) { sum=sum+i; i++; } printf(“%d”,sum); }

100

说明: 1) 如果循环体不只包 含一条语句,则应用花括号 括起来形成一个复合语句。 2) 在循环体中应有使 循环趋于结束的语句,避免 出现死循环。在本例中,设 置循环条件为i<=100,然后 有 i++ 使循环趋于结束,这 样就不会出现死循环。

5

说明:(补充内容) 3) 用作循环条件的 表达式可以是各种类型的 表达式或数值类型。如: while(1)、while (–2)、 while(‘a’) 等。 4) 小心循环变量的 “边界值”,注意循环次 数。对条件表达式的计算 次数要比循环体的执行次 数多一次。如右例:

main ( ) { int n = 0 ; while ( n + + < = 1 ) printf (“ %d \n ” , n ) ; printf (“ %d \n ” , n ) ; } 运行结果:

6

说明:
5) 不要在 while (表达式) 后加分号。如例6.2若误写成:

main ( ) { int i , sum = 0 ; 此分号使 while 的循环体为空 i=1; while ( i < = 100 ) ; { sum = sum + i ; i++; } printf ( “%d” , sum ) ; }
则程序将出现“死” 循环,无法得到正确结果。
7

6.4 do-while语句
一般形式: do 循环体语句

while (表达式);
流程图:

循环体语句 非0

表达式
0
8

例 6.3 用do-while语句求

n ?1 main( ) { int i,sum=0; i=1; do { sum=sum+i; i++; } while ( i<=100 ); /* 别忘了,这里有分号 */ printf(“%d”,sum); }

?n

100

9

讨论:while语句与do-while语句之间的异同点
1 )对同一问题可以用 while 语句处理,也可以用 do-while 语句处理。do-while结构和while结构可以相互转换。我 们可以认为 do-while 结构是由一个复合语句 (while 结构 的循环体)加一个while结构构成。比如:

do
{ sum=sum+i;
等价于

i++;
} while ( i<=100 );

sum=sum+i; i++; while ( i<=100 ) { sum=sum+i; i++; }
10

2)在一般情况下,用while语句和用do-while语句处 理同一问题时,若二者的循环体部分一样,则它们的结果 也一样。但是,对于while后面的表达式一开始就为0值时, 两种循环结构的执行结果是不同的。 ? 对于while语句,循环体可能一次也不执行;而dowhile语句,循环体至少要执行一次。 ? 对于while语句,循环体的执行次数要比循环条件的判 断次数少一次;而do-while语句,循环体的执行次数和循 环条件的判断次数是相同的。

11

6.5 for语句
一般形式: for (表达式1; 表达式2; 表达式3) 语句 执行过程:

for (表达式1; 表达式2; 表达式3) 语句

12

例:for(i=1;i<=100;i++) sum=sum+i;

i=1


i<=100


sum=sum+i i++

14

说明: (1)表达式1可以省略,此时应在for语句之前给循环变 量赋初值(设定循环初始条件)。比如: for(i=1;i<=100;i++) sum=sum+i ; 可写为: i=1; for( ;i<=100;i++) sum=sum+i ; (2)表达式2也可以省略。即没有循环终止条件,循环 无条件进行。这时,需要在循环体中加入用于跳出 循环的控制语句,否则就会出现死循环。比如: for(i=1; ;i++) /* 分号不能省略 */ { sum+=i; if(i>=100) break; }

15

(3)表达式3可以省略,但此时应另外设法修改循环变 量,保证循环能正常结束。比如: for(i=1;i<=100;i++) sum=sum+i ; 可写为: for(i=1;i<=100; ) { sum=sum+i ; i++ ; } (4)表达式1、2、3可同时省略。比如: i=1; sum=0; for( ; ; ) { sum+=i++ ; if( i >100) break; }
16

(5)表达式1、2、3都可以为任何表达式。比如:表达式1和 表达式3可以是逗号表达式,即包含一个以上的简单表 达式,中间用逗号间隔。 例1:for(i=1,sum=0; i<=100; i++) sum=sum+i ;

例2:for(i=0; (c=getchar())!=‘\n’; i++) ; 请问:此语句的作用是什么?

/* 分号不能少*/

此语句的作用是不断读入字符,并统计所输入字符的 个数,直到输入一个“换行符”为止。

17

例如:int i, j, k=0; for(i=0,j=100; i<=j; i++,j - -) k+=i+j ; printf(“%d,%d,%d”,i, j, k); 输出结果是什么?循环体可以被执行多少次?

输出结果为:51, 49, 5100

循环体被执行51次。

0, 1, 2, …, 49, 50, 50, 51, …, 98, 99, 100

19

讨论:for语句与while语句之间的异同点
1)for语句简单、方便,使用灵活,不仅可以用于循环次 数已经确定的情况,还可以用于循环次数不确定而只 给出循环结束条件的情况,它完全可以取代while语句。 在使用上,for语句更灵活,功能更强。 2)for语句和while语句之间是可以相互转换的。当省略 for语句的表达式1、3,而只给出表达式2时,就等同 于一个while语句。比如:

for ( ; i <=100; ) { sum=sum+i ; i++ ; }

while ( i <=100 ) { sum=sum+i ; i++ ; }
20

6.6 循环的嵌套
C语言中,允许三种循环结构(while循环、do-while循环 和for循环)相互嵌套和进行多层嵌套。 例如: for( i=0; i<10; i++) for( j=0; j<10; j++) for( k=0; k<10; k++) { printf(“i=%d, j=%d, k=%d\n”,i,j,k); } 此程序运行后,屏幕上将输出多少行信息? 这些信息分别是什么?
21

6.7 四种循环结构之间的比较(前已提及)

6.8 break语句和continue语句
6.8.1 break语句 一般形式: break; 作用:只能用于循环结构和switch结构,使执行流程从相应 结构中跳出,程序继续往后执行。 例:for(r=1;r<=10;r++) { area=pi*r*r; if (area>100) break; printf(“%f”,area); }

22

6.8.2 continue语句
一般形式: continue; 作用:结束本次循环,即跳过循环体中下面尚未执行的 语句,接着进行下一次是否执行循环体的判断。 contiune语句和break语句的区别是: contiune语句只是结束本次循环,即跳过本次循环 体中下面尚未执行的部分;而break语句是终止整 个循环,即退出循环结构。

详细的流程图分析,可参见教科书P115之图6.10和图6.11.
例如:

23

例6.5 输出100~200之间的不能被3整除的所有数;

main ( ) { int n; for (n=100;n<=200;n++) { if (n%3==0) continue; printf(“%d ”,n); } }

24

6.9 程序举例
例 6.6 用 求

?

的*似值,直到最后一

项的绝对值小于10-6为止。N-S流程图见左下方。

t=1, pi=0, n=1, s=1

变量说明: s为分子,也用来切换正负号;

当|t|>= 10-6 pi=pi+t n=n+2 s=-s t=s/n pi=pi*4 输出pi

n为分母;
t为相加项;

25

源程序如下:
#include <math.h> 注意几点: main ( ) 1、s 和n 可同时定义为int 或 { int s; 者float 型吗?为什么? float n,t,pi; t=1;pi=0;n=1.0;s=1; (P116.c) while((fabs(t))>1e-6) 2、若将n、t、pi 定义为 { pi=pi+t; double 型,精度提高到1e – 8 , n=n+2; 会有什么效果? s=-s; (P116_2.c) t=s/n; } pi=pi*4; printf(“pi=%10.6f\n”,pi); }
26

例6.7 求Fibonacci数列的前40个数。

Fibonacci数列通式为:

F1 ? 1

(n ? 1)

F2 ? 1 (n ? 2) Fn ? Fn ?1 ? Fn ? 2 (n ? 3)
例如,前面几项分别为: 1, 1, 2, 3, 5, 8, 13, … 这是一个古典的数学问 题,比较简单。在P116–117 和P124均有论述。 请同学们掌握。 N-S 流程图为: f1=1, f2=1 for i=1 to 20 输出f1, f2 f1=f1+f2 f2=f2+f1
27

源程序为:
main ( ) { long int f1, f2; int i; f1=1;f2=1; for(i=1; i<=20; i++)

{ printf(“%12ld %12ld”,f1,f2);
if (i%2==0) printf(“\n”); f1=f1+f2; /* 前一个数 */

f2=f2+f1;
} }

/* 后一个数 */

28

例6.8 判断m是否为素数。
读入m k=sqrt(m) i=2 当i <= k m被 i整除 真 假

定义:m 是素数的条件是不能被2, 3, …… , m-1整除。这也是素数的原始 定义。据此,有如下判断素数的算法: 算法1:直接采用定义,用m去除以2 到 m-1 。但是,当m很大时此算法的运算 量也很大,效率不高。

用break 结束循环
i=i+1 i>= k+1





输出:m是 输出:m不是 素数 素数
29

源程序如下:
#include<math.h> main( ) { int m,i,k; scanf(“%d”,&m); k=sqrt(m); for (i=2;i<=k;i++) if (m%i==0) break; if (i>=k+1) /* 请问用i = = k+1或i > k可以吗?*/

printf(“%d is prime number\n”,m);
else printf(“%d is not prime number\n”,m);

}
30

例6.9 求100-200间的全部素数。(算法同例6.8 ) 例6.10 译密码。对字符的处理办法为: 先判定它是大写字符还是小写字符,然后再将其值加4, 变成其后的第四个字母。如果加4后字符值大于‘Z’或‘z’, 则在加4的基础上减去26,转换为字母表前面的字母。 (参见P119图6.15) #include <stdio.h>
main ( ) { char c; while((c=gechar( ))!=‘\n’) { if ((c>=‘a’&&c<=‘z’| |(c>=‘A’&&c<=‘Z’)) { c=c+4; if (c>’Z’&&c<=‘Z’+4| |c>’z’) c=c-26; } 这里为什么要这样写, printf(“%c”,c); 请看附录I ASCII码表。 } }
31

第六章 循环控制 小结
§6.1 §6.2 §6.3 §6.4 §6.5 §6.6 §6.7 §6.8 §6.9 概述 goto语句以及用goto语句构成循环 while语句 do-while语句 for语句 循环的嵌套 几种循环的比较 break和continue语句 程序举例
32


相关推荐

最新更新

猜你喜欢