1
2009-7-29
第 5章 循环结构的实现
§ 1 用 go to语句实现循环
§ 2 do循环
§ 3 当型循环的实现
§ 4 直到型循环的实现
§ 5 本章小结
2
2009-7-29
顺序结构?分支选择结构
eT F
语句 1
语句 2
语句 N
循环结构语句 N
语句 M
本章的主要内容
------引 言 ------
3
2009-7-29
【 引例 】 计算 k = 12+22+…+10 2
k=0
i=0
5 i=i+1
k=k+i*i
if(i.lt.10) go to 5
write(*,*) k
end
循环体
两个概念循 环,某段程序的连续重复执行过程 。
循环体,被重复执行的那段程序 。
4
2009-7-29
§ 1 用 go to语句实现循环 (p99-100)
go to语句的一般形式为:
go to <语句标号 >
功能,当执行到该语句时,程序流程转到语句标号所对应的语句继续执行。
例如:
像此例这样的无限循环,它的实用性并不强。
在编程中,go to语句常与逻辑 if语句相结合,以构成有限循环。
100 read(*,*)no,score
write(*,*)no,score
go to 100
§ 1 用 go to语句实现循环
5
2009-7-29
例如:
本例功能:依次输入并输出 30个学生的学号及成绩。
此例是一个直到型循环的例子。即 先执行、后判断),,直到,所给条件满足为止。
对循环次数固定的循环,采用 DO循环最方便。
n=1
100 read(*,*)no,score
write(*,*)no,score
n=n+1
if(n.le.30) go to 100
§ 1 用 go to语句实现循环
6
2009-7-29
F
T
§ 2 do循环 (p100-112)
【 引例 】 依次输入并输出 30个学生的学号及成绩。
do 100,n=1,30,1
read(*,*)no,score
100 write(*,*)no,score
end
1?n
n≤30?
输出 no,
score
输入 no,
score
n+1?n
§ 2 do循环直观的执行过程
7
2009-7-29
一,do循环结构的一般形式把 do语句简写为:
其中,s是循环体最后一条语句的标号,用于标识循环体的范围。 循环体最后一条语句称为循环终端语句,s为循环终端语句标号 。
do s [,] v = e1,e2 [,e3]
循环终端语句标号
do 语句标号 [,] 循环变量 =表达式 1,表达式 2 [,表达式 3]
语句标号循环体
do语句或循环语句
§ 2 do循环循环变量初值循环变量终值循环变量步长循环变量
8
2009-7-29
§ 2 do循环
do s [,] v = e1,e2 [,e3]
do语句的有关说明:
① e3可有可无,不写时,意味着 e3=1,即步长为 1。
② 循环变量 v和 e1,e2,e3可以是整型、实型、双精度型。
如,do 10,t=5.0,25.0,1.5
③ 循环次数 r的计算公式为:
)3 312i n t ( e eeer
如,do 10,i=1,10,2
5)5i n t ()211i n t ()2 2110i n t (r
14)3.14i n t ()5.1 5.21i n t ()5.1 5.10.50.25i n t (r
9
2009-7-29
§ 2 do循环
④ e1,e2,e3的值可以为正或负; e1,e2可以为零,
但步长 e3不能为零 (若为零则是死循环 )。
若计算的循环次数 r<0,按 r=0处理,即循环一次也不执行。
步长 e3为正数和负数,循环的判断条件是不同的 。
如:
如,do 10,t=5.0,-5.0,-1.5
7)67.7i n t ()5.1 5.11i n t ()5.1 5.10.50.5i n t (r
do 10,i=1,10,2
10 write(*,*)i*i
do 10,i=10,1,-2
10 write(*,*)i*i
10
2009-7-29
§ 2 do循环
do 10,i=1,10,2
10 write(*,*)i*i
do 10,i=10,1,-2
10 write(*,*)i*I

1?i
输出 i*i
i+2?i

10?i
输出 i*i
i-2?i
是否i≤10? i≥1?
当步长 e3为正数时,循环执行的条件是 v ≤e2;
当步长 e3为负数时,循环执行的条件是 v ≥ e2。
11
2009-7-29
§ 2 do循环
⑤ 若循环变量 v的类型与 e1,e2,e3的类型不一致,则首先将 e1,e2,e3的类型转化为 循环变量 的类型,然后再进行其它的操作。
如:
为避免错误,应使循环变量 v的类型与 e1,e2,e3
的类型一致。
由于计算机中实数的近似性,应尽量避免使用实型的循环变量,最好采用 整型循环变量 。
do 10,i=1.5,3.6,1.2
do 10,i=1,3,1
取整二,do循环的执行过程( 与理解有差别)
do 10,i=1.0,3.0,0.5
12
2009-7-29

§ 2 do循环
r-1?r

v+e3?v
e1?v
计算循环次数 r
r>0?
执行循环体否P?

v+e3?v
e1?v
执行循环体
P是循环执行的条件
当 e3>0,P为 v≤e2
当 e3<0,P为 v≥e2
Fortran中 do
循环的真实执行过程可以理解为的执行过程
13
2009-7-29
do s,v = e1,e2,e3
s
循环体
§ 2 do循环三、循环终端语句是循环体的最后一条语句。
并非所有的语句都可以做循环终端语句 。
① 在 Fortran可执行语句中,除 go to、块 if结构中的 if
语句,else语句,else if语句,end if语句,end,stop、
return之外的语句可以作为循环终端语句。
可执行语句:程序在运行时可以产生某些操作,如赋值操作、输出操作。(定义见 p48,清单见 p327附录 1)
② 所有的非执行语句都不能作为循环终端语句。
非执行语句:只在编译时作出处理,运行时不产生操作,如变量类型定义语句。
14
由于上述限制,在某些情况下循环终止语句无法确定。如,输入 10个实数,分别计算其中正数、负数个数和各自的平均值:
nz=0
nf=0
pz=0.0
pf=0.0
do 100,n=1,10
read(*,*) x
if(x.gt.0.0) then
nz=nz+1
pz=pz+x
else
nf=nf+1
pf=pf+x
100 end if
pz=pz/nz
pf=pf/nf
write(*,*)nz,pz,nf,pf
end
错误
2009-7-29
15
2009-7-29
为了避免使用错误并使 do循环规范化,常采用
continue语句 (称为继续语句 )作为循环终端语句,
相应的 do循环 (称为规范化 do循环 )一般形式为:
如:
建议采用这种规范化的 do循环形式。
do s,v = e1,e2,e3
s continue
循 环 体
§ 2 do循环
do 10,i=1,10,2
write(*,*)i*i
10 continue
continue语句的功能,不执行任何操作,仅使程序流程继续执行。
16
2009-7-29
§ 2 do循环
【 例 5.1】 计算,n由键盘输入。
n
1i
is u m
编程思路:
1、输入 n的值;
2、使用一个变量 sum存放累加结果;
3、用 DO循环来实现 n次累加;
4、输出 sum的值。
17
2009-7-29
write(*,*)'请输入 n值,'
read(*,*)n
sum=0.0
do 10,i=1,n,1
sum=sum+i
10 continue
write(*,*)'sum=',sum
end
每次执行,sum
的值增加 i
问题:如果计算,程序如何修改?
n
i
is u m
1
/1
§ 2 do循环
18
2009-7-29
【 例 5.2】 计算 n!,n由键盘输入。
§ 2 do循环
write(*,*)'请输入 n值,'
read(*,*)n
t=1
do 100,i=1,n,1
t=t*i
100 continue
write(*,*)'n!=',t
end
对于第 i次循环,
相当于,ti= ti-1*i
即 i!= (i-1)!*i
相当于,t0=1
19
2009-7-29
§ 2 do循环
【 例 5.3】 计算,n由键盘输入。
n
i
i
1
!/1
write(*,*)'请输入 n值,'
read(*,*)n
t=1
sum=0
do 100,i=1,n,1
t=t/i
sum=sum+t
100 continue
write(*,*)'和 =',sum
end
设,变量 sum代表和,变量 t代表第 i项(即 1/i!)。
20
2009-7-29
【 例 5.4】 求其中 x,n由键盘输入。
!...!! n
x
3
x
2
xx1e n32x
§ 2 do循环变量 t代表 的第 i项( i=
1,2,…,n),则 。
!...!! n
x
3
x
2
xx n32
i
xtt
1ii
设:变量 sum代表右边的和,其初值为 1;
21
2009-7-29
write(*,*)'请输入 n,x的值,'
read(*,*)n,x
t=1
sum=1
do 100,i=1,n,1
t=t*x/i
sum=sum+t
100 continue
write(*,*)'exp(',x,')=',sum
end
§ 2 do循环
22
2009-7-29
【 例 5.5】 读程序,写出执行结果。
sum1=0
sum2=0
do 10,m=10,1,-1
if(mod(m,2).ne.0) then
sum1=sum1+m
else
sum2=sum2+m
end if
10 continue
write(*,*)'sum1=',sum1
write(*,*)'sum2=',sum2
end
§ 2 do循环
sum1
=9+7+5+3+1=25.0
sum2
=10+8+6+4+2=30.0
sum1=25.0
sum2=30.0
输出结果:
23
2009-7-29
§ 2 do循环四,do循环的规定
① 循环变量可以在循环体中被使用,但 其值不能被改变 。
如:
② 循环次数在执行循环前已根据 e1,e2,e3值计算好,在执行循环体期间,不因 e1,e2,e3值的改变而变;即 e1,e2,e3值在循环体中可以改变,但循环次数不会变化 。
do 10,n=1,100
n=2*n
write(*,*)n
10 continue
错误!
do s [,] v = e1,e2 [,e3]
24
2009-7-29
如:
③ 可以从循环体内转移到循环体外,也可以在循环体内部转移,但 不能从循环体外转移到循环体内 。
§ 2 do循环
l=1
m=100
n=2
do 10,i=l,m,n
l=2*l
m=m+1
n=n/2
write(*,*)l,m,n
10 continue
25
2009-7-29
五,do循环的嵌套(多重循环)
在一个 do循环中又完整地包含另一个 do循环,
称为 do循环的嵌套。
例如,二重循环:
§ 2 do循环
do s1,v1 = e1,e2,e3

do s2,v2 = x1,x2,x3

s2 continue

s1 continue
内循环外循环
26
2009-7-29
§ 2 do循环
do s1,v1 = e1,e2,e3

do s2,v2 = x1,x2,x3

s2 continue

do s3,v3 = k1,k2,k3

s3 continue

s1 continue
内循环内循环外循环
27
2009-7-29
do 10 i=l1,l2,l3

do 20 j=m1,m2,m3

do 30 k=l1,l2,l3

30 continue

20 continue

10 continue
§ 2 do循环三重循环:
内循环外循环中循环
28
2009-7-29
【 例 5.6】 计算 1!,3!,5!,7!。
思路,用外层循环控制上述自然数的变化,用内层循环计算各数的阶乘。
t=1
do 10,i=1,7,2
do 20,j=1,i
t=t*j
20 continue
write(*,*)i,'!=',t
10 continue
end
§ 2 do循环有问题!如何修改?
29
2009-7-29
【 例 5.7】 打印九九乘法口诀表。
1× 1= 1
2× 1= 2
2× 2= 4
3× 1= 3
3× 2= 6
3× 3= 9
.
.
.
9× 9= 81
§ 2 do循环
30
2009-7-29
do 10,i=1,9
do 20,j=1,i
write(*,*) i,'*',j,'=',i*j
20 continue
write(*,*)
10 continue
end
§ 2 do循环
write(*,30) i,j,i*j
30 format ( \,1x,i1,'*',i1,'=',i2 )
31
2009-7-29
【 例 5.8】 百钱买百鸡问题。
公鸡每只 5元、母鸡每只 3元、小鸡 1元 3只,花
100元买三种鸡共 100只,问其中公鸡、母鸡、小鸡各有多少只?
设变量 x,y,z分别为公鸡数、母鸡和小鸡数,
则有以下方程组:
方程组有多组解,利用“枚举法”。



100
3
z
y3x5
100zyx


300zy9x15
100zyx
§ 2 do循环
32
2009-7-29
integer x,y,z
write(*,*)' 公鸡 母鸡 小鸡 '
do 10,x=0,100
do 20,y=0,100
z=100-x-y
if(15*x+9*y+z.eq.300)write(*,*)x,y,z
20 continue
10 continue
end
§ 2 do循环
33
2009-7-29
do循环是当型循环的一种,当循环次数已知时,
使用 do循环比较方便。 当循环次数无法事先确定时,一般不使用 do循环。如:
当型循环,对给定的条件,当条件满足时就执行循环体,否则循环结束。(先判断,后执行)
实现方法,① do while循环
② 用块 if结构和 go to语句实现
§ 3 当型循环的实现 (p113-118)
【 例 5.9】 求为止。,直至 6
nn32
x 10
!n
x
!n
x...
!3
x
!2
xx1e
§ 3 当型循环的实现
34
2009-7-29
一,do while循环一般形式为:
功能,当逻辑表达式成立时,反复执行循环体中的语句;当逻辑表达式不成立时结束循环。
do s,while(逻辑表达式 )
循环体
s continue
【 例 5.9】 为止。,直至 6nn32x 10
!n
x
!n
x...
!3
x
!2
xx1e
§ 3 当型循环的实现设 sum代表右边的和,初值为 1;
变量 t代表第 i项,即,则 。
!i
xt i
i? i
xtt
1ii
35
2009-7-29
write(*,*)'请输入 x的值,'
read(*,*)x
i=1
t=1
sum=1
do 10,while( abs(t).ge.1e-6 )
t=t*x/i
sum=sum+t
i=i+1
10 continue
write(*,*)'exp(',x,')=',sum
end
§ 3 当型循环的实现
36
2009-7-29
【 例 5.10】 读程序,说出执行结果。
s=0
k=5
do 10,while(k.lt.100)
s=s+k
k=k+5
10 continue
write(*,*)'s=',s
end
结果:
100以内 5的倍数的那些数之和。
§ 3 当型循环的实现
37
2009-7-29
【 例 5.11】 读程序,说出执行结果。
§ 3 当型循环的实现
a=0
b=0
k=1
do 10,while(k.le.10)
a=a+k
b=b+k*k
k=k+1
10 continue
write(*,*)'a=',a
write(*,*)'b=',b
end
结果:
a=前 10个自然数的和
b=前 10个自然数的平方和
38
2009-7-29
【 例 5.12】 利用 do while循环 判断正整数 m是否为素数。
素数:只能被 1和自身整除的数。
算法思路如下:
1、输入正整数 m。
2、将 m作为被除数,依次将 2~ m-1作为除数 i,对每个除数 i 进行判断(循环):
若不能被 m整除,则对下一个数进行判断;
若能被 m整数,则不再对后面的数进行判断。
3、若每个除数都不能被 m整数,则退出循环后 i=m>m-1
,即 m是素数;
若有除数被 m整数,则退出循环后 i≤m-1,即 m不是素数。
§ 3 当型循环的实现
39
2009-7-29
write(*,*)'请输入一个正整数,'
read(*,*)m
k= m-1
i=2
do 10,while( i.le.k,and,mod(m,i).ne.0 )
i=i+1
10 continue
if(i.gt.k) then
write(*,*)m,'是素数 '
else
write(*,*)m,'不是素数 '
end if
end
§ 3 当型循环的实现
sqrt(m)m/2
40
2009-7-29
【 例 5.13】 找出 100到 500之间的所有素数 。
do 5,m=101,500,2
k=m-1
i=2
do 10,while( i.le.k,and,mod(m,i).ne.0 )
i=i+1
10 continue
if(i.gt.k) then
write(*,30)m
30 format(\,1x,i3)
end if
5 continue
end
§ 3 当型循环的实现
41
2009-7-29
§ 3 当型循环的实现注意,do while循环不是 Fortran77国际标准中的语句,但它是 Fortran90标准中的语句,且大多数 Fortran系统均支持该语句(包括 Compaq
Visual Fortran系统)。
二、用块 if结构和 go to语句实现当型循环这是 Fortran77标准实现的方式,其一般形式为:
s if (逻辑表达式 ) then
循环体
go to s
end if
42
2009-7-29
【 例 5.14】 计算
100
1
99
1
4
1
3
1
2
11s
s=0
i=1
10 if(i.le.100) then
t=1.0/i
if(mod(i,2),eq,0) t=-t
s=s+t
i=i+1
go to 10
end if
write(*,*)'s=',s
end
§ 3 当型循环的实现循环体
43
2009-7-29
§ 4 直到型循环的实现 (p119-124)
实现方法:
① do until循环 (不属于 Fortran77标准)
② 用逻辑 if语句实现 (属于 Fortran77标准)
一,do until循环一般形式为:
执行过程,先执行循环体;后判断逻辑表达式:
若为,true.则退出循环,若为,false.则继续执行循环,.true.是退出循环的条件 。
do s,until(逻辑表达式 )
循环体
s continue
§ 4 直到型循环的实现
44
2009-7-29
do s,until(逻辑表达式 )
循环体
s continue
注意,虽然判断条件写在前面,但仍然是“先执行循环体,后判断条件”。
容易出现混淆,不推荐使用。
二、用逻辑 if语句实现直到型循环其中 s是循环体中第一个语句的语句标号。
s 循环体
if (逻辑表达式 ) go to s
§ 4 直到型循环的实现
45
2009-7-29
s 循环体
if (逻辑表达式 ) go to s
执行过程,先执行循环体;后判断逻辑表达式:
若为,true.则继续执行循环,若为,false.则退出循环、往下执行,此条件是执行循环的条件 。
虽然与 do until的判断条件作用相反,但这种形式(先执行、后判断)仍然认为是直到型循环的一种。
【 例 5.15】 用直到型循环实现:
为止。,直至 6
nn32
x 10
!n
x
!n
x...
!3
x
!2
xx1e
§ 4 直到型循环的实现
46
2009-7-29
write(*,*)'请输入 x的值,'
read(*,*)x
i=1
t=1
sum=1
do 10,while( abs(t).ge.1e-6 )
t=t*x/i
sum=sum+t
i=i+1
10 continue
write(*,*)'exp(',x,')=',sum
end
10 t=t*x/i
sum=sum+t
i=i+1
if( abs(t).ge.1e-6 ) go to 10
§ 4 直到型循环的实现
47
2009-7-29
a=0
b=0
k=10
10 if(k,lt,10)then
a=a+k
b=b+k*k
k=k+1
go to 10
end if
print*,a,b
§ 4 直到型循环的实现
a=0
b=0
k=10
10 a=a+k
b=b+k*k
k=k+1
if(k,lt,10)go to 10
end if
print*,a,b
例:下面两段程序 a,b的值分别为多少?
a,b的值均为 0 a,b的值为 10,100
48
2009-7-29
一、循环结构的分类循环结构可分为 do,当型 和 直到型 三种。严格地讲,应是两种循环结构,因为 do循环也是当型循环结构。
当型循环实现方法,① do while循环 ;② 用块 if结构和 go to语句实现 。
直到型循环实现方法,① do until循环 (不推荐使用); ② 用逻辑 if语句实现 。
§ 5 本章小结 (p124-125)
§ 5 本章小结
49
2009-7-29
二、同一个问题可以用不同的循环结构实现:
若循环次数事先已知,既可以使用 do循环,
也可以使用当型循环和直到型循环。
例如:计算 N!。
若循环次数事先无法确定,只能使用当型或直到型。
三、不同类型的循环结构可以互相嵌套,但一个循环必须完整地包含在另一个循环之中。
§ 5 本章小结
50
2009-7-29