第 六 章 循环控制用于解决语句的重复执行,以克服一条语句只能执行一次的限制 。
几种简要的循环结构
break 和 continue 语句
for 语句的变化形式
循环嵌套第六章 循环控制
问题:
10求 sum=? i
i=1
int sum;
sum = 1+2+3+4+5+6+7+8+9+10;
100求 sum=? i?
i=1
n
求 sum=? i? ( n由键盘输入)
i=1
第六章 循环控制
问题:
10求 sum=? i
i=1
i=1; sum=0;
sum = 部分累加和 + i (i=1~~10)
sum = sum + i ; i++;
………,十行
sum = sum + i ; i ++;
goto 语句以及用 goto语句构成循环一般形式,goto 语句标号;
其中标号是一个有效的标识符,这个标识符加上一个,,” 一起出现在函数内某处,执行 goto语句后,程序将跳转到该标号处并执行其后的语句。
另外标号必须与 goto语句同处于一个函数中,但可以不在一个循环层中。通常 goto语句与 if条件语句连用,当满足某一条件时,程序跳到标号处运行。
例 6.1使用 goto语句实现求解 1~ 100累计和
main()
{ int n=1,sum=0;
loop,sum += n; n++;
if (n<=100) goto loop;
printf(“sum=%d\n”,
sum);
}
,loop:”为语句标号其命名遵循标识符命名规则。
goto语句格式,goto
标号,功能为:使系统转向标号所在的语句行执行。
注意,
结构化程序设计方法,主张限制使用
goto语句。因为滥用 goto语句,将会导致程序结构无规律、可读性差。
另外,从功能上说,for语句可完全代替当型循环语句 while,所以该语句也不是必需的。
for 语句
1.用 for 语句实现
#include <stdio.h>
main()
{
int i,sum=0;
for (i=1; i<=10; i++)
sum=sum+i;
printf("%d",sum);
}
重复执行的语句规定重复次数
i< 0; i +)
for 语句
for 语句格式,
for( 初值表达式 ; 循环继续表达式 ; 循环变化表达式)
一条要反复执行的语句 ;
三个独立的表达式
for (i=1; i<=10; i++)
sum=sum+i;
循环 继续 表达式
for 语句
for 语句格式,
for( 初值表达式 ; 循环继续表达式 ; 循环变化表达式)
一条要反复执行的语句 ;
执行流程:
循环变量 初值 表达式一条要反复执行的语句循环变量 变化 表达式 下一条语句不满足
i<=10
for 语句执行流程:
i=1
sum=sum+i
i++ printf("%d",sum);
不满足循环结构后面的语句
for (i=1; i<=10; i++)
sum=sum+i;
for 语句
从键盘输入 100个整数,求其中正数之和 。
#include <stdio.h>
main()
{
int i,sum =0,x ;
for (i=0; i<100; i++) {
scanf(“%d”,&x);
if (x>0) sum=sum+x;
}
printf("%d",sum);
}
重复步骤:
1 输入一个数
2 对正数求和
共重复 100次
for 语句
从键盘输入 100个整数,求其中正数的 平均数 。
#include <stdio.h>
main() {
int i,count=0,x ;
float sum=0;
for (i=0; i<100; i++)
{ scanf(“%d”,&x);
if (x>0) { sum=sum+x; count++; }
}
sum / = count ;
printf("%f",sum);
}
for 语句
用 for语句实现 10+9+8+7+6+5+4+3+2+1
#include <stdio.h>
main()
{
int i,sum=0;
for (i=10; i>0; i- -)
sum=sum+i;
printf("%d",sum);
}
while 语句
while (条件 )
重复执行的 一条 语句;
不满足满足重复执行的语句;
后一语句 ;
条件?
复合语句
while 语句
while 实现要点整个循环由 i 控制,i 称 循环变量
i=1; 循环变量必须有初值
while (i<=10) 继续循环的条件
{ sum=sum+i;
i++; 循环变量的改变
}
循环体例 6.2 用 while语句求 1~ 100的累计和
main()
{ int i=1,sum=0; /*初始化循环控制变量 i和累计器
sum*/
while( i<=100 )
{ sum += i; /*实现累加 */
i++; /*循环控制变量 i增 1*/
}
printf(“sum=%d\n”,sum);
}
程序运行情况如下:
sum=5050
循环体如果包括一个以上语句,应该用花括号括起来,
形成复合语句
while 语句
for 语句与 while 语句比较
main()
{ int i,sum=0; i=1;
for (i=1; i<=10; i++) while (i<=10)
sum=sum+i; { sum=sum+i;
printf("%d",sum); i++; }
}
do-while 语句
用 do-while 语句实现
do-while 语句格式:
do 一条要反复执行的语句 ;
while ( 条件表达式 )
while 是先判别条件,再决定是否循环;
do-while 是先至少循环一次,然后再根据循环的结果决定是否继续循环 。
do-while 语句
do-while 语句实现流程要反复执行的语句循环表达式非 0=0
下一条语句先循环后判断
重复步骤:
1 输入一个数
2 求和
重复直到 0
do-while 语句
do....while 与 while 的用法有所不同例:输入一串正数求和,
直到数据为 0结束。
main( )
{ int x,sum=0;
do {
scanf(“%d”,&x);
sum+ = x ;
} while (x>0)
printf(“sum=%d”,sum);
}
例:输入一串正数求和,
直到数据为非正数结束。
main( )
{ int x,sum=0;
while (x>0) {
sum+ = x ;
scanf(“%d”,&x);
}
printf(“sum=%d”,sum);
}
s -x);
scanf(“%d”,&x);
编写数列求和程序,
1+ 1/2+1/3+1/4+….+1/ n
main( )
{ int i,n; float y=0;
scanf(“%d”,&n);
for (i=1; i<=n; i++)
y+=1.0/ i ;
printf("n=%dy=%f\n",n,y);
}
1/1+1/2+1/3+1/4+….+1/ n
循环结构的实现循环实现要点,(1) 找出什么要反复执行
(2) 重复到何时结束假定输入 x=12345,逆序输出 。 从低位开始分割
12345 %10 = 5
12345 /10 =1234
1234 %10 = 4
1234/10 =123
123%10 = 3
123/10 =12
12%10 = 2
12/10 =1
1%10=1
1/10=0 结束
12345 %10 = 5
如何 12345 ---> 4?
(1) 12345%100/10
(2) 12345/10%10
(1)反复执行 x%10
x=x/10
(2)何时结束 x= =0
scanf(,%d”,&x) ;
while ( x>0 )
{ printf(,%d,,x%10) ;
x=x/10 ;
}
循环结构的实现循环实现要点,(1) 找出什么要反复执行
(2) 重复到何时结束假定输入 x=12345 顺序输出,从高位开始分割
12345 /10000 = 1
12345 %10000 =2345
2345 /1000 = 2
2345%1000 =345
345 /100 = 3
345%100 =45
45 /10 = 4
45%10 =5
5/1= 5
5%1=5
(1)开始如何得到 10000
找输入数据的位数
d=1;
for ( i=10; x/i>0 ; i=i*10)
d++ ;
(2) 每次循环缩小 10倍
(3) 缩小到 0 结束
§ 6.2 break 和 continue 语句例:读入一行字符 ( 不超过 10个 ),给予输出
#include "stdio.h"
main()
{ char c;
int i=0;
for (i=0;i<10;i++) /* i>=10 是结束条件 */
{ c=getchar();
putchar(c);
}
}
if (c=='\n') break;
/* c==回车 也是结束条件 */
有两个条件决定循环的结束
main()
{ char c;
int i=0;
for (i=0; i<10 && c! ='\n'; i++)
{ putchar(c); 两个结束条件合并
c=getchar();
}
}
c=getchar();
真 ( 非 0)
break 流程
for的下一条语句假 ( 0)
表达式 1
表达式 2
语 句 1
表达式 3
否 break
语 句 2
循环体是程序:
for (表 1;表 2;表 3)
{ 语句 1 ;
if (,.,) break ;
语句 2 ;
}
for后的下一条语句;
是真 ( 非 0)
continue 流程
for的下一条语句假 ( 0)
表达式 1
表达式 2
语 句 1
表达式 3
否continue
语 句 2
循环体程序:
for (表 1;表 2;表 3)
{ 语句 1 ;
if (,.,) continue;
语句 2 ;
}
for后的下一条语句;
continue 语句例子
#include "stdio.h"
main()
{ char c;
int i;
for (i=0;i<10;i++) /* i>=10 是结束条件 */
{ c=getchar();
if (c=='\n') continue;
putchar(c); /* c=回车 也是结束条件 */
}
} 问,若把 break 改成 continue,
结果会怎样?
输入,abc ↙
efgh ↙
123 ↙
输出,abcefgh1
§ 6.3 for 语句的变化形式原形,int i,sum=0;
for (i=1; i<=10; i++) sum=sum+i;
i<=10
sum=0;
i=1;
sum=sum+i
i++
下一条语句变形 1 int i=1,sum=0;
for ( ;i<=10; i++) sum= sum+i;
变形 2 int i=1,sum=0;
for ( ; i<=10 ; )
{ sum = sum+i; i++; }
相当于,while
§ 6.3 for 语句的变化形式原形,int i,sum=0;
for (i=1; i<=10; i++) sum=sum+i;
i<=10
sum=0;
i=1;
sum=sum+i
i++
下一条语句变形 3 int i=1,sum=0;
for( ; ; ){
无限循环 sum=sum+i ; i++ }
变形 4 int i,sum;
for(i=1,sum=0;i<=10;sum+=i,i++);
无循环体语句
if (i>10) break;
§ 6.3 for 语句的变化形式原形,int i,sum=0;
for (i=1; i<=10; i++) sum=sum+i;
变形1 int i=1,sum=0;
for ( ; i<=10; i++) sum=sum+i ;
变形2 int i=1,sum=0;
for ( ; i<=10 ; ) { sum=sum+i; i++; }
变形3 int i=1,sum=0;
for ( ; ; ) { if (i>10) break;
无限循环 sum=sum+i ; i++ }
变形4 int i,sum;
for (i=1,sum=0 ; i<=10; sum+=i,i++) ;
不管那一种变形,循环变量的初值、判断和变化表达式仍都存在,只是改变了所处的位置。
不管那一种变形,三个表达式的 功能 缺一不可,且执行流程不得改变。
原形,int i,sum=0;
for (i=1; i<=10; i++) sum=sum+i;
i<=10
i=1;
sum=0;
sum=sum+i
i++
下一条语句变形 3 int i=1,sum=0;
for( ; ; ){ if (i>10) break;
sum=sum+i ; i++ }
变形 4 int i,sum;
for(i=1,sum=0;i<=10;sum+=i,i++);
无循环体语句
§ 6.4循环嵌套循环体中又包含了循环语句称循环嵌套。
例:求 S = 1! +2! +3! + …… + n!
分析,首先要循环 n次来累加 i!
for (i=1; i<=n; i++)
s = s + i! ;
如果存在求阶乘的运算 !,计算完成。
嵌套
for (i=1; i<=n; i++)
{ t = i! ;
s = s + t ;
}
for (t=1,j=1 ; j<=i; j++)
t = t * j ;t = t * i ;
§ 6.4循环嵌套例:已知小鸡 0.5文钱/只,公鸡2文钱/只,
母鸡3文钱/只,现要求 100文钱正好买 100只鸡,
请给出所有的组合。
组合问题用计算机解,通常采取“凑”的办法母鸡可能的只数,0——100
公鸡可能的只数,0——100
小鸡可能的只数,0——100
然后对三种鸡所 有的 组合方式,排除不等于
100元和 100只的那些组合。
hen
cock
chick
§ 6.4循环嵌套
main()
{
int chick,cock,hen;
for (cock=0; cock<=100; cock++)
for (hen=0; hen<=100; hen++)
for (chick=0; chick<=100; chick++)
if (cock+hen+chick= =100 &&
cock*2+hen*3+chick*0.5 = = 100)
printf("cock=%d hen=%d
chick=%d\n",cock,hen,chick);
}
cock=0
hen=0
chick=0
100
1100
1100
§ 6.4循环嵌套运行结果:
cock=0 hen=20 chick=80
cock=5 hen=17 chick=78
cock=10 hen=14 chick=76
cock=15 hen=11 chick=74
cock=20 hen=8 chick=72
cock=25 hen=5 chick=70
cock=30 hen=2 chick=68
§ 6.4循环嵌套运行过程:
cock=0
hen=0 chick=0~100 共 101次
hen=1 chick=0~100 共 101次……
hen=100 chick=0~100 共 101次
cock=1
hen=0 chick=0~100 共 101次
……hen=100 chick=0~100 共 101次
……cock=100
hen=0 chick=0~100 共 101次……
hen=100 chick=0~100 共 101次
101
次
101
次
101
次
100
多万次
§ 6.4循环嵌套
main()
{
int chick,cock,hen;
for (cock=0; cock<=50; cock++)
for (hen=0; hen<=33; hen++)
{ chick = 100 - cock - hen ;
if (cock*2+hen*3+chick*0.5 = = 100)
printf("cock=%d hen=%d
chick=%d\n",cock,hen,chick);
}
}
§ 6.4循环嵌套循环嵌套均是大循环包小循环绝对不允许循环体交叉 !
for ( )
{,........
do {
..........
}
} while(....)
for ( )
{,.......,
do {
.........,
} while(....)
}
§ 6.4循环嵌套
main()
{
int chick,cock,hen ;
for (cock=0; cock<=50; cock++)
{ for (hen=0; hen<=33; hen++)
{ chick = 100 - cock - hen ;
if (cock*2+hen*3+chick*0.5 = = 100)
break;
}
printf(.........) ;
}
}
§ 6.4循环嵌套
main()
{
int chick,cock,hen,flag=0 ;
for (cock=0; cock<=50; cock++)
{ for (hen=0; hen<=33; hen++)
{ chick = 100 - cock - hen ;
if (cock*2+hen*3+chick*0.5 = = 100)
{ flag =1; break; }
}
if (flag) break ;
printf(.........) ;
}
}
“接力赛”第一棒
“接力赛”第二棒结论,break只能终止内层循环例题求算式直到第 40项的和
main()
{ int i,s=1;
float y=0;
for (i=1; i<=40; i++)
{ y=y+s/((float)i*( i+1)) ;
s=-s ;
}
printf(,%f”,y);
}
421301201121611
第 i 项,1/(i*(i+1))
符号,s = 1
s = -1
例题求算式直到第 40项的和
main()
{ int i,s=-1;
float y=1;
for (i=2; i<=40; i++)
{ y=y+s/((float)i*( i+1)) ;
s=-s ;
}
printf(,%f”,y);
}
421301201121611
第 i 项,1/(i*(i+1))
符号,s = 1
s = -1
例题编程,输出下列形式的九九乘法表 。
(1) (2) (3) (4) (5) (6) (7) (8) (9)
(1) 1 2 3 4 5 6 7 8 9
(2) 2 4 6 8 10 12 14 16 18
(3) 3 6 9 12 15 18 21 24 27
(4) 4 8 12 16 20 24 28 32 36
(5) 5 10 15 20 25 30 35 40 45
(6) 6 12 18 24 30 36 42 48 54
(7) 7 14 21 28 35 42 49 56 63
(8) 8 16 24 32 40 48 56 64 72
(9) 9 18 27 36 45 54 63 72 81
#include <stdio.h>
main()
{ int i,j;
printf(" "); 第 1行先输出 5个空格
for(i=1;i<10;i++) printf("(%d) ",i);
putchar('\n');
for(i=1;i<10;i++) { i代表行
printf("(%d) ",i);
for(j=1;j<10;j++) j代表列
printf(" %2d",i*j);
putchar('\n');
}
}
例题下列程序求 Sn=a+aa+aaa+……+aa…aa(n个 a)的值,
sn=2+22+222+2222+22222,其值应为 24690。
#include <stdio.h>
main()
{
int a,n,count=1,sn=0,tn=0;
scanf(“%d%d”,&a,&n);
for (count=1; count <=n ;count++){
tn=tn*10+a;
sn=sn+tn;
}
printf(“the sn is,%d \n”,sn);
}
tn=0*10+2 =2
tn=2*10+2=22
tn=22*10+2=222
程序举例
1,输入一行字符,统计其中的单词数,单词之间用空格分隔开。
例如:输入 you are a student,则有 4个单词。
解题思路:
( 1)用空格区分每一个单词;
( 2)遇到空格,则表示前一个单词结束; (word=0)
( 3) 遇到一个非空格:若前面一个字符是空格 (即
word=0),则开始一个新单词 (word=1,计数加 1);
若前面一个字符是非空格 (即 word=1),则仍然是同一个单词 。
#include <stdio.h>
main()
{
char string[81];
int i,num=0,word=0;
gets(string);
for (i = 0; string[i]!=?\0?;i++)
if (string[i]==) word = 0;
else if (word == 0) {
word++; num++;
}
printf(“There are %d words in the line.\n”,num);
}
程序举例
2.打印以下图案,
$
$ $ $
$ $ $ $ $
$ $ $ $ $ $ $
$ $ $ $ $
$ $ $
$
分析:分上下两部分考虑
对上半部每一行,$数 +空格数 =列数 (n)
行数 $数 空格数 (单边 )
$ 1 1 (n-1)/2
$ $ $ 2 2*2-1=3 (n-3)/2
$ $ $ $ $ 3 2*3-1=5 (n-5)/2
$ $ $ $ $ $ $ 4 2*4-1=7 (n-7)/2
一般地,i 2*i-1 (n-(2*i-1))/2
分析:
对下半部每一行,$数 +空格数 =列数 (n)
行数 空格数 (单边 ) $数
$ 1 1 n-1*2
$ $ $ 2 2 n-2*2
$ $ $ $ $ 3 3 n-3*2
$ $ $ $ $ $ $ i i n-i*2
$ $ $ $ $
$ $ $
$
#include <stdio.h>
main()
{
int n_blank,n_dollar,i,j,n,m;
scanf(“%d”,&n);
m=(n+1)/2;
for (i = 1; i <= m; i++) {
n_dollar = 2 * i – 1;
n_blank = (n – n_dollar)/2;
for (j = 0; j < n_blank; j++)
putchar();
for (j = 0; j < n_dollar; j++)
putchar(?$?);
putchar(?\n?);
}
for (i = 1; i < m; i++) {
n_blank = i;
n_dollar = n – 2 * n_blank;
for (j = 0; j < n_blank; j++)
putchar();
for (j = 0; j < n_dollar; j++)
putchar(?$?);
putchar(?\n?);
}
return 0;
}
例 6.6用公式求 π 直到某一项的绝对值小于 10-6
#include<math.h>
main()
{
int s;
float n,t,pi;
t=1,pi=0;n=1.0;s=1;
while(fabs(t)>1e-6)
{pi=pi+t;
n=n+2;
s=-s;
t=s/n;
}
pi=pi*4;
printf("pi=%10.6f\n",pi);
}
[例 6.7] 求 Fibonacci数列的前 40个数。该数列的生成方法为,F1=1,F2=1,Fn=Fn-1+Fn-2
( n>=3),即从第 3个数开始,每个数等于前 2
个数之和。
f1=1,f2=1
for i=1 to 20
输出 f1,f2
f1=f1+f2
f2=f2+f1
main()
{ long int f1=1,f2=1; /*定义并初始化数列的头 2个数 */
int i=1; /*定义并初始化循环控制变量 i*/
for(i=1 ; i<=20; i++ ) /*1组 2个,20组 40个数 */
{ printf(“%15ld%15ld”,f1,f2); /*输出当前的 2
个数 */
if(i%2==0) printf(“\n”); /*输出 2次( 4个数),
换行 */
f1 += f2;
f2 += f1; /*计算下 2个数 */
}
}
1
5
34
233
1597
10946
75025
514229
3524578
24157817
1
8
55
377
2584
17711
121393
832040
5702887
39088169
2
13
89
610
4181
28657
196418
1346269
9227465
63245986
3
21
144
987
6765
46368
317811
2178309
14930352
102334155
例 6,8 判断 m是否素数读入 m
k=?m
i=2
当 i?k
m被 i整除真 假用 break
结束循环
i=i+1
i?k+1真 假输出,m”是素数,输出,m”不 是素数,
#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) printf(“%d is a prime number\n”,m);
else printf(“%d is not a prime number\n”,m);
}
例 6.9 求 100至 200间的全部素数 。
#include<math.h>
main()
{
int m,i,k,n=0;
for(m=101;m<=200;m=m+2)
{
k=sqrt(m);
for(i=2;i<=k;i++)
if(m%i==0)break;
if(i>=k+1)
{printf(“%d”,m);
n=n+1;}
if(n%n==0)printf(“\n”);
}
printf(“\n”);
}
例 6.10 译密码 。
程序中对输入的字符处理办法是:先判定它是否大写字母或小写字母,若是,则将其值加 4(变成其后的第 4个字母 )。 如果加 4
以后字符值大干 ‘ Z’或,z,
则表示原来的字母在 V(或 v)
之后,应按图所示的规律将它转换为 A—D(或 a—d)之一 。 办法是使 c减 26.
几种简要的循环结构
break 和 continue 语句
for 语句的变化形式
循环嵌套第六章 循环控制
问题:
10求 sum=? i
i=1
int sum;
sum = 1+2+3+4+5+6+7+8+9+10;
100求 sum=? i?
i=1
n
求 sum=? i? ( n由键盘输入)
i=1
第六章 循环控制
问题:
10求 sum=? i
i=1
i=1; sum=0;
sum = 部分累加和 + i (i=1~~10)
sum = sum + i ; i++;
………,十行
sum = sum + i ; i ++;
goto 语句以及用 goto语句构成循环一般形式,goto 语句标号;
其中标号是一个有效的标识符,这个标识符加上一个,,” 一起出现在函数内某处,执行 goto语句后,程序将跳转到该标号处并执行其后的语句。
另外标号必须与 goto语句同处于一个函数中,但可以不在一个循环层中。通常 goto语句与 if条件语句连用,当满足某一条件时,程序跳到标号处运行。
例 6.1使用 goto语句实现求解 1~ 100累计和
main()
{ int n=1,sum=0;
loop,sum += n; n++;
if (n<=100) goto loop;
printf(“sum=%d\n”,
sum);
}
,loop:”为语句标号其命名遵循标识符命名规则。
goto语句格式,goto
标号,功能为:使系统转向标号所在的语句行执行。
注意,
结构化程序设计方法,主张限制使用
goto语句。因为滥用 goto语句,将会导致程序结构无规律、可读性差。
另外,从功能上说,for语句可完全代替当型循环语句 while,所以该语句也不是必需的。
for 语句
1.用 for 语句实现
#include <stdio.h>
main()
{
int i,sum=0;
for (i=1; i<=10; i++)
sum=sum+i;
printf("%d",sum);
}
重复执行的语句规定重复次数
i< 0; i +)
for 语句
for 语句格式,
for( 初值表达式 ; 循环继续表达式 ; 循环变化表达式)
一条要反复执行的语句 ;
三个独立的表达式
for (i=1; i<=10; i++)
sum=sum+i;
循环 继续 表达式
for 语句
for 语句格式,
for( 初值表达式 ; 循环继续表达式 ; 循环变化表达式)
一条要反复执行的语句 ;
执行流程:
循环变量 初值 表达式一条要反复执行的语句循环变量 变化 表达式 下一条语句不满足
i<=10
for 语句执行流程:
i=1
sum=sum+i
i++ printf("%d",sum);
不满足循环结构后面的语句
for (i=1; i<=10; i++)
sum=sum+i;
for 语句
从键盘输入 100个整数,求其中正数之和 。
#include <stdio.h>
main()
{
int i,sum =0,x ;
for (i=0; i<100; i++) {
scanf(“%d”,&x);
if (x>0) sum=sum+x;
}
printf("%d",sum);
}
重复步骤:
1 输入一个数
2 对正数求和
共重复 100次
for 语句
从键盘输入 100个整数,求其中正数的 平均数 。
#include <stdio.h>
main() {
int i,count=0,x ;
float sum=0;
for (i=0; i<100; i++)
{ scanf(“%d”,&x);
if (x>0) { sum=sum+x; count++; }
}
sum / = count ;
printf("%f",sum);
}
for 语句
用 for语句实现 10+9+8+7+6+5+4+3+2+1
#include <stdio.h>
main()
{
int i,sum=0;
for (i=10; i>0; i- -)
sum=sum+i;
printf("%d",sum);
}
while 语句
while (条件 )
重复执行的 一条 语句;
不满足满足重复执行的语句;
后一语句 ;
条件?
复合语句
while 语句
while 实现要点整个循环由 i 控制,i 称 循环变量
i=1; 循环变量必须有初值
while (i<=10) 继续循环的条件
{ sum=sum+i;
i++; 循环变量的改变
}
循环体例 6.2 用 while语句求 1~ 100的累计和
main()
{ int i=1,sum=0; /*初始化循环控制变量 i和累计器
sum*/
while( i<=100 )
{ sum += i; /*实现累加 */
i++; /*循环控制变量 i增 1*/
}
printf(“sum=%d\n”,sum);
}
程序运行情况如下:
sum=5050
循环体如果包括一个以上语句,应该用花括号括起来,
形成复合语句
while 语句
for 语句与 while 语句比较
main()
{ int i,sum=0; i=1;
for (i=1; i<=10; i++) while (i<=10)
sum=sum+i; { sum=sum+i;
printf("%d",sum); i++; }
}
do-while 语句
用 do-while 语句实现
do-while 语句格式:
do 一条要反复执行的语句 ;
while ( 条件表达式 )
while 是先判别条件,再决定是否循环;
do-while 是先至少循环一次,然后再根据循环的结果决定是否继续循环 。
do-while 语句
do-while 语句实现流程要反复执行的语句循环表达式非 0=0
下一条语句先循环后判断
重复步骤:
1 输入一个数
2 求和
重复直到 0
do-while 语句
do....while 与 while 的用法有所不同例:输入一串正数求和,
直到数据为 0结束。
main( )
{ int x,sum=0;
do {
scanf(“%d”,&x);
sum+ = x ;
} while (x>0)
printf(“sum=%d”,sum);
}
例:输入一串正数求和,
直到数据为非正数结束。
main( )
{ int x,sum=0;
while (x>0) {
sum+ = x ;
scanf(“%d”,&x);
}
printf(“sum=%d”,sum);
}
s -x);
scanf(“%d”,&x);
编写数列求和程序,
1+ 1/2+1/3+1/4+….+1/ n
main( )
{ int i,n; float y=0;
scanf(“%d”,&n);
for (i=1; i<=n; i++)
y+=1.0/ i ;
printf("n=%dy=%f\n",n,y);
}
1/1+1/2+1/3+1/4+….+1/ n
循环结构的实现循环实现要点,(1) 找出什么要反复执行
(2) 重复到何时结束假定输入 x=12345,逆序输出 。 从低位开始分割
12345 %10 = 5
12345 /10 =1234
1234 %10 = 4
1234/10 =123
123%10 = 3
123/10 =12
12%10 = 2
12/10 =1
1%10=1
1/10=0 结束
12345 %10 = 5
如何 12345 ---> 4?
(1) 12345%100/10
(2) 12345/10%10
(1)反复执行 x%10
x=x/10
(2)何时结束 x= =0
scanf(,%d”,&x) ;
while ( x>0 )
{ printf(,%d,,x%10) ;
x=x/10 ;
}
循环结构的实现循环实现要点,(1) 找出什么要反复执行
(2) 重复到何时结束假定输入 x=12345 顺序输出,从高位开始分割
12345 /10000 = 1
12345 %10000 =2345
2345 /1000 = 2
2345%1000 =345
345 /100 = 3
345%100 =45
45 /10 = 4
45%10 =5
5/1= 5
5%1=5
(1)开始如何得到 10000
找输入数据的位数
d=1;
for ( i=10; x/i>0 ; i=i*10)
d++ ;
(2) 每次循环缩小 10倍
(3) 缩小到 0 结束
§ 6.2 break 和 continue 语句例:读入一行字符 ( 不超过 10个 ),给予输出
#include "stdio.h"
main()
{ char c;
int i=0;
for (i=0;i<10;i++) /* i>=10 是结束条件 */
{ c=getchar();
putchar(c);
}
}
if (c=='\n') break;
/* c==回车 也是结束条件 */
有两个条件决定循环的结束
main()
{ char c;
int i=0;
for (i=0; i<10 && c! ='\n'; i++)
{ putchar(c); 两个结束条件合并
c=getchar();
}
}
c=getchar();
真 ( 非 0)
break 流程
for的下一条语句假 ( 0)
表达式 1
表达式 2
语 句 1
表达式 3
否 break
语 句 2
循环体是程序:
for (表 1;表 2;表 3)
{ 语句 1 ;
if (,.,) break ;
语句 2 ;
}
for后的下一条语句;
是真 ( 非 0)
continue 流程
for的下一条语句假 ( 0)
表达式 1
表达式 2
语 句 1
表达式 3
否continue
语 句 2
循环体程序:
for (表 1;表 2;表 3)
{ 语句 1 ;
if (,.,) continue;
语句 2 ;
}
for后的下一条语句;
continue 语句例子
#include "stdio.h"
main()
{ char c;
int i;
for (i=0;i<10;i++) /* i>=10 是结束条件 */
{ c=getchar();
if (c=='\n') continue;
putchar(c); /* c=回车 也是结束条件 */
}
} 问,若把 break 改成 continue,
结果会怎样?
输入,abc ↙
efgh ↙
123 ↙
输出,abcefgh1
§ 6.3 for 语句的变化形式原形,int i,sum=0;
for (i=1; i<=10; i++) sum=sum+i;
i<=10
sum=0;
i=1;
sum=sum+i
i++
下一条语句变形 1 int i=1,sum=0;
for ( ;i<=10; i++) sum= sum+i;
变形 2 int i=1,sum=0;
for ( ; i<=10 ; )
{ sum = sum+i; i++; }
相当于,while
§ 6.3 for 语句的变化形式原形,int i,sum=0;
for (i=1; i<=10; i++) sum=sum+i;
i<=10
sum=0;
i=1;
sum=sum+i
i++
下一条语句变形 3 int i=1,sum=0;
for( ; ; ){
无限循环 sum=sum+i ; i++ }
变形 4 int i,sum;
for(i=1,sum=0;i<=10;sum+=i,i++);
无循环体语句
if (i>10) break;
§ 6.3 for 语句的变化形式原形,int i,sum=0;
for (i=1; i<=10; i++) sum=sum+i;
变形1 int i=1,sum=0;
for ( ; i<=10; i++) sum=sum+i ;
变形2 int i=1,sum=0;
for ( ; i<=10 ; ) { sum=sum+i; i++; }
变形3 int i=1,sum=0;
for ( ; ; ) { if (i>10) break;
无限循环 sum=sum+i ; i++ }
变形4 int i,sum;
for (i=1,sum=0 ; i<=10; sum+=i,i++) ;
不管那一种变形,循环变量的初值、判断和变化表达式仍都存在,只是改变了所处的位置。
不管那一种变形,三个表达式的 功能 缺一不可,且执行流程不得改变。
原形,int i,sum=0;
for (i=1; i<=10; i++) sum=sum+i;
i<=10
i=1;
sum=0;
sum=sum+i
i++
下一条语句变形 3 int i=1,sum=0;
for( ; ; ){ if (i>10) break;
sum=sum+i ; i++ }
变形 4 int i,sum;
for(i=1,sum=0;i<=10;sum+=i,i++);
无循环体语句
§ 6.4循环嵌套循环体中又包含了循环语句称循环嵌套。
例:求 S = 1! +2! +3! + …… + n!
分析,首先要循环 n次来累加 i!
for (i=1; i<=n; i++)
s = s + i! ;
如果存在求阶乘的运算 !,计算完成。
嵌套
for (i=1; i<=n; i++)
{ t = i! ;
s = s + t ;
}
for (t=1,j=1 ; j<=i; j++)
t = t * j ;t = t * i ;
§ 6.4循环嵌套例:已知小鸡 0.5文钱/只,公鸡2文钱/只,
母鸡3文钱/只,现要求 100文钱正好买 100只鸡,
请给出所有的组合。
组合问题用计算机解,通常采取“凑”的办法母鸡可能的只数,0——100
公鸡可能的只数,0——100
小鸡可能的只数,0——100
然后对三种鸡所 有的 组合方式,排除不等于
100元和 100只的那些组合。
hen
cock
chick
§ 6.4循环嵌套
main()
{
int chick,cock,hen;
for (cock=0; cock<=100; cock++)
for (hen=0; hen<=100; hen++)
for (chick=0; chick<=100; chick++)
if (cock+hen+chick= =100 &&
cock*2+hen*3+chick*0.5 = = 100)
printf("cock=%d hen=%d
chick=%d\n",cock,hen,chick);
}
cock=0
hen=0
chick=0
100
1100
1100
§ 6.4循环嵌套运行结果:
cock=0 hen=20 chick=80
cock=5 hen=17 chick=78
cock=10 hen=14 chick=76
cock=15 hen=11 chick=74
cock=20 hen=8 chick=72
cock=25 hen=5 chick=70
cock=30 hen=2 chick=68
§ 6.4循环嵌套运行过程:
cock=0
hen=0 chick=0~100 共 101次
hen=1 chick=0~100 共 101次……
hen=100 chick=0~100 共 101次
cock=1
hen=0 chick=0~100 共 101次
……hen=100 chick=0~100 共 101次
……cock=100
hen=0 chick=0~100 共 101次……
hen=100 chick=0~100 共 101次
101
次
101
次
101
次
100
多万次
§ 6.4循环嵌套
main()
{
int chick,cock,hen;
for (cock=0; cock<=50; cock++)
for (hen=0; hen<=33; hen++)
{ chick = 100 - cock - hen ;
if (cock*2+hen*3+chick*0.5 = = 100)
printf("cock=%d hen=%d
chick=%d\n",cock,hen,chick);
}
}
§ 6.4循环嵌套循环嵌套均是大循环包小循环绝对不允许循环体交叉 !
for ( )
{,........
do {
..........
}
} while(....)
for ( )
{,.......,
do {
.........,
} while(....)
}
§ 6.4循环嵌套
main()
{
int chick,cock,hen ;
for (cock=0; cock<=50; cock++)
{ for (hen=0; hen<=33; hen++)
{ chick = 100 - cock - hen ;
if (cock*2+hen*3+chick*0.5 = = 100)
break;
}
printf(.........) ;
}
}
§ 6.4循环嵌套
main()
{
int chick,cock,hen,flag=0 ;
for (cock=0; cock<=50; cock++)
{ for (hen=0; hen<=33; hen++)
{ chick = 100 - cock - hen ;
if (cock*2+hen*3+chick*0.5 = = 100)
{ flag =1; break; }
}
if (flag) break ;
printf(.........) ;
}
}
“接力赛”第一棒
“接力赛”第二棒结论,break只能终止内层循环例题求算式直到第 40项的和
main()
{ int i,s=1;
float y=0;
for (i=1; i<=40; i++)
{ y=y+s/((float)i*( i+1)) ;
s=-s ;
}
printf(,%f”,y);
}
421301201121611
第 i 项,1/(i*(i+1))
符号,s = 1
s = -1
例题求算式直到第 40项的和
main()
{ int i,s=-1;
float y=1;
for (i=2; i<=40; i++)
{ y=y+s/((float)i*( i+1)) ;
s=-s ;
}
printf(,%f”,y);
}
421301201121611
第 i 项,1/(i*(i+1))
符号,s = 1
s = -1
例题编程,输出下列形式的九九乘法表 。
(1) (2) (3) (4) (5) (6) (7) (8) (9)
(1) 1 2 3 4 5 6 7 8 9
(2) 2 4 6 8 10 12 14 16 18
(3) 3 6 9 12 15 18 21 24 27
(4) 4 8 12 16 20 24 28 32 36
(5) 5 10 15 20 25 30 35 40 45
(6) 6 12 18 24 30 36 42 48 54
(7) 7 14 21 28 35 42 49 56 63
(8) 8 16 24 32 40 48 56 64 72
(9) 9 18 27 36 45 54 63 72 81
#include <stdio.h>
main()
{ int i,j;
printf(" "); 第 1行先输出 5个空格
for(i=1;i<10;i++) printf("(%d) ",i);
putchar('\n');
for(i=1;i<10;i++) { i代表行
printf("(%d) ",i);
for(j=1;j<10;j++) j代表列
printf(" %2d",i*j);
putchar('\n');
}
}
例题下列程序求 Sn=a+aa+aaa+……+aa…aa(n个 a)的值,
sn=2+22+222+2222+22222,其值应为 24690。
#include <stdio.h>
main()
{
int a,n,count=1,sn=0,tn=0;
scanf(“%d%d”,&a,&n);
for (count=1; count <=n ;count++){
tn=tn*10+a;
sn=sn+tn;
}
printf(“the sn is,%d \n”,sn);
}
tn=0*10+2 =2
tn=2*10+2=22
tn=22*10+2=222
程序举例
1,输入一行字符,统计其中的单词数,单词之间用空格分隔开。
例如:输入 you are a student,则有 4个单词。
解题思路:
( 1)用空格区分每一个单词;
( 2)遇到空格,则表示前一个单词结束; (word=0)
( 3) 遇到一个非空格:若前面一个字符是空格 (即
word=0),则开始一个新单词 (word=1,计数加 1);
若前面一个字符是非空格 (即 word=1),则仍然是同一个单词 。
#include <stdio.h>
main()
{
char string[81];
int i,num=0,word=0;
gets(string);
for (i = 0; string[i]!=?\0?;i++)
if (string[i]==) word = 0;
else if (word == 0) {
word++; num++;
}
printf(“There are %d words in the line.\n”,num);
}
程序举例
2.打印以下图案,
$
$ $ $
$ $ $ $ $
$ $ $ $ $ $ $
$ $ $ $ $
$ $ $
$
分析:分上下两部分考虑
对上半部每一行,$数 +空格数 =列数 (n)
行数 $数 空格数 (单边 )
$ 1 1 (n-1)/2
$ $ $ 2 2*2-1=3 (n-3)/2
$ $ $ $ $ 3 2*3-1=5 (n-5)/2
$ $ $ $ $ $ $ 4 2*4-1=7 (n-7)/2
一般地,i 2*i-1 (n-(2*i-1))/2
分析:
对下半部每一行,$数 +空格数 =列数 (n)
行数 空格数 (单边 ) $数
$ 1 1 n-1*2
$ $ $ 2 2 n-2*2
$ $ $ $ $ 3 3 n-3*2
$ $ $ $ $ $ $ i i n-i*2
$ $ $ $ $
$ $ $
$
#include <stdio.h>
main()
{
int n_blank,n_dollar,i,j,n,m;
scanf(“%d”,&n);
m=(n+1)/2;
for (i = 1; i <= m; i++) {
n_dollar = 2 * i – 1;
n_blank = (n – n_dollar)/2;
for (j = 0; j < n_blank; j++)
putchar();
for (j = 0; j < n_dollar; j++)
putchar(?$?);
putchar(?\n?);
}
for (i = 1; i < m; i++) {
n_blank = i;
n_dollar = n – 2 * n_blank;
for (j = 0; j < n_blank; j++)
putchar();
for (j = 0; j < n_dollar; j++)
putchar(?$?);
putchar(?\n?);
}
return 0;
}
例 6.6用公式求 π 直到某一项的绝对值小于 10-6
#include<math.h>
main()
{
int s;
float n,t,pi;
t=1,pi=0;n=1.0;s=1;
while(fabs(t)>1e-6)
{pi=pi+t;
n=n+2;
s=-s;
t=s/n;
}
pi=pi*4;
printf("pi=%10.6f\n",pi);
}
[例 6.7] 求 Fibonacci数列的前 40个数。该数列的生成方法为,F1=1,F2=1,Fn=Fn-1+Fn-2
( n>=3),即从第 3个数开始,每个数等于前 2
个数之和。
f1=1,f2=1
for i=1 to 20
输出 f1,f2
f1=f1+f2
f2=f2+f1
main()
{ long int f1=1,f2=1; /*定义并初始化数列的头 2个数 */
int i=1; /*定义并初始化循环控制变量 i*/
for(i=1 ; i<=20; i++ ) /*1组 2个,20组 40个数 */
{ printf(“%15ld%15ld”,f1,f2); /*输出当前的 2
个数 */
if(i%2==0) printf(“\n”); /*输出 2次( 4个数),
换行 */
f1 += f2;
f2 += f1; /*计算下 2个数 */
}
}
1
5
34
233
1597
10946
75025
514229
3524578
24157817
1
8
55
377
2584
17711
121393
832040
5702887
39088169
2
13
89
610
4181
28657
196418
1346269
9227465
63245986
3
21
144
987
6765
46368
317811
2178309
14930352
102334155
例 6,8 判断 m是否素数读入 m
k=?m
i=2
当 i?k
m被 i整除真 假用 break
结束循环
i=i+1
i?k+1真 假输出,m”是素数,输出,m”不 是素数,
#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) printf(“%d is a prime number\n”,m);
else printf(“%d is not a prime number\n”,m);
}
例 6.9 求 100至 200间的全部素数 。
#include<math.h>
main()
{
int m,i,k,n=0;
for(m=101;m<=200;m=m+2)
{
k=sqrt(m);
for(i=2;i<=k;i++)
if(m%i==0)break;
if(i>=k+1)
{printf(“%d”,m);
n=n+1;}
if(n%n==0)printf(“\n”);
}
printf(“\n”);
}
例 6.10 译密码 。
程序中对输入的字符处理办法是:先判定它是否大写字母或小写字母,若是,则将其值加 4(变成其后的第 4个字母 )。 如果加 4
以后字符值大干 ‘ Z’或,z,
则表示原来的字母在 V(或 v)
之后,应按图所示的规律将它转换为 A—D(或 a—d)之一 。 办法是使 c减 26.