《C语言程序设计第6章循环控制结构ppt课件》由会员分享,可在线阅读,更多相关《C语言程序设计第6章循环控制结构ppt课件(63页珍藏版)》请在金锄头文库上搜索。
1、第第第第6 6 6 6章章章章 循循循循环环控制构造控制构造控制构造控制构造2024/8/252/63本章学本章学习内容内容 计计数控制的循数控制的循环环 条件控制的循条件控制的循环环 for语语句,句,while语语句,句,do-while语语句句 continue语语句,句,break语语句句 嵌套循嵌套循环环 构造化程序构造化程序设计设计的根本思想的根本思想 程序程序调试调试与排与排错错2024/8/253/63Example:Example:如何确定程如何确定程序的序的输入和入和输出呢出呢?Draw a flowchart for the following problem:读入5个整
2、数,计算并显示它们的和.Input : 5 个整数个整数n1, n2, n3, n4, n5 Output: n1, n2, n3, n4, n5的和的和Input example: 2 3 4 5 6Output example: 20问题问题的提出的提出的提出的提出2024/8/254/63Input n1Input n2Input n3input n4input n5output sumsum n1+n2+n3+n4+n52 2n1Assume input example: 2 3 4 5 63 3n24 4n35 5n46 6n52020sumend运用了运用了6个不同的个不同的变量量
3、start问题问题的提出的提出的提出的提出2024/8/255/636.1循循环环控制构造与循控制构造与循环语环语句句标标志控制志控制志控制志控制Sentinel Sentinel ControlledControlled计计数控制数控制数控制数控制Counter ControlledCounter Controlled1, 2, 3, 4, 1, 2, 3, 4, , 4, 3, 2, 1, 4, 3, 2, 1条件控制条件控制条件控制条件控制Condition Condition ControlledControlled如何如何如何如何对对循循循循环进环进展控制呢展控制呢展控制呢展控制呢?
4、 ?2024/8/256/63counter 1, sum 0counter6sum sum + nfalsetruecounter+output suminput n1countersum01 6true2n0 + 2222 6true32 + 3533 6true45 + 4944 6true59 + 51455 6true614 + 62066 6falsecounter-controlled 计数器每次增数器每次增1运用了运用了3个个变量量Assume input example: 2 3 4 5 66.26.2计计计计数控制的循数控制的循数控制的循数控制的循环环环环startend2
5、024/8/257/636.2计计数控制的循数控制的循环环counter initialValuecounter initialValuetest countertest counterStep nStep xfalsetrueUpdate counterUpdate counter循循循循环环体体体体Body of Body of LoopLoop 2024/8/258/63当型循当型循环Condition is tested first 计数控制数控制Loop is controlled by a counterSyntaxfor (initial value ; condition; u
6、pdate counter) statement;Orfor (initial value ; condition; update counter) statement;statement; for循循环语环语句句循循循循环环起始条件起始条件起始条件起始条件循循循循环终环终了条件了条件了条件了条件循循循循环变环变量增量增量增量增值值复合语句复合语句compound statement被当作一条语句对待被当作一条语句对待循环变量控制循环次循环变量控制循环次数,不要在循环体内数,不要在循环体内改动这个变量的值改动这个变量的值2024/8/259/63i 0, sum 0i 5sumsum+ nfa
7、lsetruei+output suminput nint i, sum, n;sum = 0;for (i = 0; i 5; i+) scanf(“%d, &n);sum = sum + n;printf(“%d, sum);for循循环语环语句句startend2024/8/2510/63A直直到到型型循循环假假真真6.3条件控制的循条件控制的循环环A当当型型循循环真真假假假2024/8/2511/63 当型循环Condition is tested first 条件或计数控制 Loop is controlled by condition or a counter 语法while (c
8、ondition) statement; Orwhile (condition) statement;statement;No semicolon!No semicolon!while循循环语环语句句2024/8/2512/63直到型循直到型循环Statements in the loop are executed first (at least once), and condition is tested last条件或条件或计数控制数控制 Loop is controlled by condition or a counter 语法法do statement; statement; whi
9、le (condition) ;statement;Dont forget the Dont forget the semicolon!semicolon!do-while循循环语环语句句2024/8/2513/63【例【例6.1】计计算并算并输输出出1+2+3+n的的值值 循循循循环环次数知,次数知,次数知,次数知,计计数控制的循数控制的循数控制的循数控制的循环环2024/8/2514/63 循循循循环环次数知,次数知,次数知,次数知,计计数控制的循数控制的循数控制的循数控制的循环环【例【例6.1】计计算并算并输输出出1+2+3+n的的值值sum = 0的作用?的作用? 2024/8/251
10、5/63 循循循循环环次数知,次数知,次数知,次数知,计计数控制的循数控制的循数控制的循数控制的循环环【例【例6.1】计计算并算并输输出出1+2+3+n的的值值2024/8/2516/63循循环条件第一次就条件第一次就为假如假如输入入-1时会怎会怎样? 【例【例6.1】计计算并算并输输出出1+2+3+n的的值值2024/8/2517/63A当当型型循循环真真假假假假 Testing Condition First【例【例6.1】计计算并算并输输出出1+2+3+n的的值值2024/8/2518/63直直到到型型循循环A假真真A假假Testing condition last 【例【例6.1】计计
11、算并算并输输出出1+2+3+n的的值值2024/8/2519/63留意留意 在在在在forfor和和和和whilewhile语语句之后普通没有分号句之后普通没有分号句之后普通没有分号句之后普通没有分号 有分号表示循有分号表示循有分号表示循有分号表示循环环体就是分号之前的内容体就是分号之前的内容体就是分号之前的内容体就是分号之前的内容 空空空空语语句句句句表示循表示循表示循表示循环环体内什么都不做体内什么都不做体内什么都不做体内什么都不做 while (i 100); while (i 100); i+; i+; 死循死循死循死循环环 for (i = 0; i 100; i+); for (i
12、 = 0; i 100; i+); printf(%d, i); printf(%d, i); 用于延用于延用于延用于延时时留意!留意!2024/8/2520/63 如何减少循如何减少循如何减少循如何减少循环环的次数?的次数?的次数?的次数?【例【例6.1】计计算并算并输输出出1+2+3+n的的值值2024/8/2521/63【例【例6.1】计计算并算并输输出出1+2+3+n的的值值2024/8/2522/63逗号运算符逗号运算符Comma Operator 多数情况下,并不运用整个逗号表达式的多数情况下,并不运用整个逗号表达式的多数情况下,并不运用整个逗号表达式的多数情况下,并不运用整个逗号
13、表达式的值值,更,更,更,更常常常常见见的情况是要分的情况是要分的情况是要分的情况是要分别别得到各表达式的得到各表达式的得到各表达式的得到各表达式的值值 主要用在循主要用在循主要用在循主要用在循环语环语句中,同句中,同句中,同句中,同时对时对多个多个多个多个变变量量量量赋赋初初初初值值等等等等 for (i = 1 , j = 100; i j; i+, j-) for (i = 1 , j = 100; i j; i+, j-) for (i = 1 , j = 100; i j; i+, j-) for (i = 1 , j = 100; i j; i+, j-)表达式表达式表达式表达式1
14、, 1, 表达式表达式表达式表达式2, , 2, , 表达式表达式表达式表达式n n循循环起始条件起始条件循循环变量增量增值循循环终了条件了条件2024/8/2523/63【例【例6.3】计计算并算并输输出出n! = 1 2 3 n 2024/8/2524/63【例【例6.4】计计算并算并输输出出1!, 2!, 3!, , n! 2024/8/2525/63 假假假假设设用用用用户户不慎不慎不慎不慎输输入了非法字符,那么先去除入了非法字符,那么先去除入了非法字符,那么先去除入了非法字符,那么先去除输输入入入入缓缓冲区冲区冲区冲区中的内容,然后提示用中的内容,然后提示用中的内容,然后提示用中的内
15、容,然后提示用户户重新重新重新重新输输入数据直到入数据直到入数据直到入数据直到输输入正确入正确入正确入正确为为止止止止【例【例6.5】输输入两个整型数,入两个整型数,计计算并算并输输出两个整数的最大出两个整数的最大值值scanf()前往前往值为值为正确正确读读入的数据入的数据项项数数 去除去除输输入入缓缓冲区中的冲区中的错误错误数据数据 2024/8/2526/63 循循循循环环次数未知,次数未知,次数未知,次数未知,标标志控制的循志控制的循志控制的循志控制的循环环标志志值Sentinel Sentinel ValueValue【例【例6.2】输输入数据,入数据,显显示每次累加示每次累加的的结
16、结果,直到果,直到输输入入0时为时为止止2024/8/2527/63 循循循循环环次数未知,次数未知,次数未知,次数未知,标标志控制的循志控制的循志控制的循志控制的循环环【例【例6.2】输输入数据,入数据,显显示每次累加示每次累加的的结结果,直到果,直到输输入入0时为时为止止2024/8/2528/63选择三种循三种循环的普通原那么的普通原那么 假假假假设设循循循循环环次数知,次数知,次数知,次数知,计计数控制的循数控制的循数控制的循数控制的循环环 用用用用forfor 假假假假设设循循循循环环次数未知,条件控制的循次数未知,条件控制的循次数未知,条件控制的循次数未知,条件控制的循环环 用用用
17、用whilewhile 假假假假设设循循循循环环体至少要体至少要体至少要体至少要执执行一次行一次行一次行一次 用用用用do-whiledo-while 这这只是只是只是只是“ “普通原那么,不是普通原那么,不是普通原那么,不是普通原那么,不是“ “原那么原那么原那么原那么2024/8/2529/63循序循序渐进式式编程程例例6.66.6:猜数游:猜数游戏想一个想一个1100之之间的数的数猜猜对: right!猜猜错:wrong!并提示并提示大小大小2024/8/2530/63只猜1次直到猜对为止最多猜10次猜多个数10次猜不对就猜下一个数循序循序渐进式式编程:猜数游程:猜数游戏例例5.4,例例
18、6.6,例例6.7,例例6.122024/8/2531/63猜数游猜数游戏用到的用到的库函数函数 怎怎怎怎样样模模模模拟计拟计算机算机算机算机“ “想一个数呢?想一个数呢?想一个数呢?想一个数呢? 随机函数随机函数随机函数随机函数rand()rand() 产产生生生生0,RAND_MAX 0,RAND_MAX 之之之之间间的随机数的随机数的随机数的随机数 magic = rand(); magic = rand(); #include #include RAND_MAXRAND_MAX在在在在stdlib.hstdlib.h中定中定中定中定义义,不大于双字,不大于双字,不大于双字,不大于双字节
19、节整数的最大整数的最大整数的最大整数的最大值值32767 32767 产产生生生生0,b-1 0,b-1 之之之之间间的随机数的随机数的随机数的随机数 magic = rand()%b;magic = rand()%b; 产产生生生生a,a+b-1 a,a+b-1 之之之之间间的随机数的随机数的随机数的随机数 magic = rand()%b + a; magic = rand()%b + a; 2024/8/2532/63#include #include #include #include main() main() int magic; /*int magic; /*计计计计算机算机算机
20、算机 想想想想 的数的数的数的数*/*/int guess; /*int guess; /*人猜的数人猜的数人猜的数人猜的数*/*/magic = rand()%100 + 1; /*“magic = rand()%100 + 1; /*“想一个想一个想一个想一个11,100100之之之之间间间间的数的数的数的数magic*/magic*/printf(Please guess a magic number:);printf(Please guess a magic number:);scanf(%d, &guess); scanf(%d, &guess); if (guess magic)i
21、f (guess magic) printf(Wrong! Too high!n); printf(Wrong! Too high!n); else if (guess magic) else if (guess magic) printf(Wrong! Too low!n); printf(Wrong! Too low!n); else else printf(Right! n); printf(Right! n); printf(The number is:%d n, magic); printf(The number is:%d n, magic); 例例5.4只猜1次2024/8/25
22、33/63#include #include #include #include main()main() int magic; int magic; int guess; int guess; int counter; /*int counter; /*记录记录记录记录人猜次数的人猜次数的人猜次数的人猜次数的计计计计数器数器数器数器变变变变量量量量*/*/magic = rand() % 100 + 1; magic = rand() % 100 + 1; counter = 0; /*counter = 0; /*计计计计数器数器数器数器变变变变量量量量countcount初始化初始化初始
23、化初始化为为为为0*/0*/dodoprintf(Please guess a magic number:);printf(Please guess a magic number:);scanf(%d, &guess); scanf(%d, &guess); counter +; /*counter +; /*计计计计数器数器数器数器变变变变量量量量countcount加加加加1*/1*/if (guess magic) if (guess magic) printf(Wrong! Too high!n); printf(Wrong! Too high!n);else if (guess ma
24、gic) else if (guess magic) printf(Wrong! Too low!n); printf(Wrong! Too low!n); else else printf(Right!n); printf(Right!n);while (guess != magic); while (guess != magic); printf(counter = %d n, counter); printf(counter = %d n, counter); 直到猜对为止例例6.62024/8/2534/63猜数游猜数游戏用到的用到的库函数函数 每次运每次运每次运每次运转转程序程序程序
25、程序时计时计算机所算机所算机所算机所“ “想的数都是一想的数都是一想的数都是一想的数都是一样样的,的,的,的,这这是什么是什么是什么是什么缘缘由呢?由呢?由呢?由呢? 函数函数函数函数rand()rand()产产生的只是生的只是生的只是生的只是伪伪随机数随机数随机数随机数 随机函数随机函数随机函数随机函数srandsrand 为为函数函数函数函数rand()rand()设设置随机数种子来置随机数种子来置随机数种子来置随机数种子来实现对实现对函数函数函数函数randrand所所所所产产生的生的生的生的伪伪随机数的随机数的随机数的随机数的 “ “随机化随机化随机化随机化 经过输经过输入随机数种子,
26、入随机数种子,入随机数种子,入随机数种子,产产生生生生0,1000,100之之之之间间的随机数的随机数的随机数的随机数 scanf(%u, &seed); scanf(%u, &seed); srand(seed); srand(seed); magic = rand() % 100 + 1; magic = rand() % 100 + 1; 2024/8/2535/63#include #include #include #include main()main() int magic; int magic; int guess; int guess; int counter; /*int
27、counter; /*记录记录记录记录人猜次数的人猜次数的人猜次数的人猜次数的计计计计数器数器数器数器变变变变量量量量*/*/ unsigned int seed; unsigned int seed; printf(Please enter seed:); printf(Please enter seed:);scanf(%u, &seed);scanf(%u, &seed);srand(seed);srand(seed);magic = rand() % 100 + 1; magic = rand() % 100 + 1; counter = 0; /*counter = 0; /*计计计
28、计数器数器数器数器变变变变量量量量countcount初始化初始化初始化初始化为为为为0*/0*/dodoprintf(Please guess a magic number:);printf(Please guess a magic number:);scanf(%d, &guess); scanf(%d, &guess); counter +; /*counter +; /*计计计计数器数器数器数器变变变变量量量量countcount加加加加1*/1*/if (guess magic) if (guess magic) printf(Wrong! Too high!n); printf(W
29、rong! Too high!n);else if (guess magic) else if (guess magic) printf(Wrong! Too low!n); printf(Wrong! Too low!n); else else printf(Right!n); printf(Right!n);while (guess != magic); while (guess != magic); printf(counter = %d n, counter); printf(counter = %d n, counter); 直到猜对为止例例6.62024/8/2536/63猜数游猜
30、数游戏用到的用到的库函数函数 运用运用运用运用计计算机算机算机算机读读取其取其取其取其时钟值时钟值并把并把并把并把该值该值自自自自动设动设置置置置为为随机随机随机随机数种子,数种子,数种子,数种子,产产生生生生0,1000,100之之之之间间的随机数的随机数的随机数的随机数 函数函数函数函数time()time()前往以秒前往以秒前往以秒前往以秒计计算的当前算的当前算的当前算的当前时间值时间值,该值该值被被被被转换为转换为无符号整数并用作随机数无符号整数并用作随机数无符号整数并用作随机数无符号整数并用作随机数发发生器的种子生器的种子生器的种子生器的种子 #include #include sr
31、and(time(NULL); srand(time(NULL); magic = rand() % 100 + 1; magic = rand() % 100 + 1; 函数函数函数函数time()time()能能能能为为程序程序程序程序员员提供代表提供代表提供代表提供代表时间时间的字符串,的字符串,的字符串,的字符串,运用运用运用运用NULLNULL作作作作为为函数参数,使其不具函数参数,使其不具函数参数,使其不具函数参数,使其不具备备此功能此功能此功能此功能2024/8/2537/63#include #include #include #include #include #includ
32、e main()main() int magic; int magic; int guess; int guess; int counter; /*int counter; /*记录记录记录记录人猜次数的人猜次数的人猜次数的人猜次数的计计计计数器数器数器数器变变变变量量量量*/*/ srand(time(NULL); srand(time(NULL);magic = rand() % 100 + 1; magic = rand() % 100 + 1; counter = 0; /*counter = 0; /*计计计计数器数器数器数器变变变变量量量量countcount初始化初始化初始化初始
33、化为为为为0*/0*/dodoprintf(Please guess a magic number:);printf(Please guess a magic number:);scanf(%d, &guess); scanf(%d, &guess); counter +; /*counter +; /*计计计计数器数器数器数器变变变变量量量量countcount加加加加1*/1*/if (guess magic) if (guess magic) printf(Wrong! Too high!n); printf(Wrong! Too high!n);else if (guess magic
34、) else if (guess magic) printf(Wrong! Too low!n); printf(Wrong! Too low!n); else else printf(Right!n); printf(Right!n);while (guess != magic); while (guess != magic); printf(counter = %d n, counter); printf(counter = %d n, counter); 直到猜对为止例例6.62024/8/2538/63#include #include #include #include #inclu
35、de #include main()main() int magic; int magic; int guess; int guess; int counter; /*int counter; /*记录记录记录记录人猜次数的人猜次数的人猜次数的人猜次数的计计计计数器数器数器数器变变变变量量量量*/*/ srand(time(NULL); srand(time(NULL); magic = rand() % 100 + 1;magic = rand() % 100 + 1; counter = 0; /*counter = 0; /*计计计计数器数器数器数器变变变变量量量量countcount初
36、始化初始化初始化初始化为为为为0*/0*/dodoprintf(Please guess a magic number:);printf(Please guess a magic number:);scanf(%d, &guess); scanf(%d, &guess); counter +; /*counter +; /*计计计计数器数器数器数器变变变变量量量量countcount加加加加1*/1*/if (guess magic) if (guess magic) printf(Wrong! Too high!n); printf(Wrong! Too high!n);else if (g
37、uess magic) else if (guess magic) printf(Wrong! Too low!n); printf(Wrong! Too low!n); else else printf(Right!n); printf(Right!n);while (guess != magic & counter 10); while (guess != magic & counter magic) if (guess magic) printf(Wrong!Too high!n); printf(Wrong!Too high!n);else if (guess magic) else
38、if (guess magic) printf(Wrong!Too low!n); printf(Wrong!Too low!n);elseelse printf(Right!n); printf(Right!n);while (guess != magic & counter 10);while (guess != magic & counter magic) if (guess magic) printf(Wrong!Too high!n); printf(Wrong!Too high!n);else if (guess magic) else if (guess magic) print
39、f(Wrong!Too low!n); printf(Wrong!Too low!n);elseelse printf(Right!n); printf(Right!n);while (guess != magic & counter 10);while (guess != magic & counter 10);printf(counter = %dn, counter); printf(counter = %dn, counter); printf(Do you want to continue(Y/N or y/n)?);printf(Do you want to continue(Y/
40、N or y/n)?);scanf( %c, &reply);scanf( %c, &reply);while (reply = Y) | (reply = y); while (reply = Y) | (reply = y); 6.4嵌套循嵌套循环环例例例例6.126.12防止非法字符防止非法字符防止非法字符防止非法字符输输入入入入2024/8/2541/63【例【例6.9】输输入入n值值,计计算并算并输输出出 1! + 2! + 3! + + n! 每次每次单独独计算算累加累加项2024/8/2542/63【例【例6.9】输输入入n值值,计计算并算并输输出出 1! + 2! + 3! +
41、 + n! 利用前利用前项计算后算后项2024/8/2543/63运用嵌套循运用嵌套循环的本卷的本卷须知知 运用复合运用复合语句,以保句,以保证逻辑上的正确性上的正确性 即用一即用一对花括号将各花括号将各层循循环体体语句括起来句括起来 内内层和外和外层循循环控制控制变量不能同名,以免呵量不能同名,以免呵斥混乱斥混乱 采用右采用右缩进格式格式书写,以保写,以保证层次的明晰性次的明晰性 留意!留意!2024/8/2544/63 breakbreak语语语语句句句句 和和和和 continue continue语语语语句句句句 对对对对forfor、whilewhile、do-whiledo-whi
42、le循循循循环进环进环进环进展内部手展内部手展内部手展内部手术术术术Break?Break?退出一退出一退出一退出一层层循循循循环环或或或或switchswitchContinue?Continue?中断此次中断此次中断此次中断此次循循循循环环,开,开,开,开场场下一次下一次下一次下一次6.5流程的流程的转转移控制移控制 2024/8/2545/63n?10Please enter n:10n = 10Please enter n: -10Program is over!【例【例6.14】 演示演示break与与continue-10#include #include main()main()
43、 int i, n;int i, n;for (i=1; i=5; i+)for (i=1; i=5; i+) printf(Please enter n:);printf(Please enter n:);scanf(%d, &n);scanf(%d, &n);if (n 0) if (n 0) break;break;printf(n = %dn, n);printf(n = %dn, n); printf(Program is over!n);printf(Program is over!n); 2024/8/2546/63n?10Please enter n:10n = 10Pleas
44、e enter n: -10Please enter n:20n = 20Please enter n: -20Please enter n:30n = 30Program is over!【例【例6.14】 演示演示break与与continue-1020-2030#include #include main()main() int i, n;int i, n;for (i=1; i=5; i+)for (i=1; i=5; i+) printf(Please enter n:);printf(Please enter n:);scanf(%d, &n);scanf(%d, &n);if (
45、n 0) if (n 0) continue;continue;printf(n = %dn, n);printf(n = %dn, n); printf(Program is over!n);printf(Program is over!n); 2024/8/2547/63 语语句句句句标标号号号号LabelLabel举举例例例例 error:error: gotogoto语语句句句句举举例例例例 goto error;goto error; 普通方式普通方式普通方式普通方式goto语语句与句与语语句句标标号号2024/8/2548/63 韩韩信有一信有一信有一信有一队队兵,他想知道有多少人
46、,便兵,他想知道有多少人,便兵,他想知道有多少人,便兵,他想知道有多少人,便让让士兵排士兵排士兵排士兵排队队报报数。按从数。按从数。按从数。按从1 1 1 1至至至至5 5 5 5报报数,最末一个士兵数,最末一个士兵数,最末一个士兵数,最末一个士兵报报的数的数的数的数为为1 1 1 1;按;按;按;按从从从从1 1 1 1至至至至6 6 6 6报报数,最末一个士兵数,最末一个士兵数,最末一个士兵数,最末一个士兵报报的数的数的数的数为为5 5 5 5;按从;按从;按从;按从1 1 1 1至至至至7 7 7 7报报数,最末一个士兵数,最末一个士兵数,最末一个士兵数,最末一个士兵报报的数的数的数的数
47、为为4 4 4 4;最后再按从;最后再按从;最后再按从;最后再按从1 1 1 1至至至至11111111报报数,最末一个士兵数,最末一个士兵数,最末一个士兵数,最末一个士兵报报的数的数的数的数为为10101010。他知道。他知道。他知道。他知道韩韩信至少有信至少有信至少有信至少有多少兵多少兵多少兵多少兵吗吗? 设设兵数兵数兵数兵数为为x x x x,那么,那么,那么,那么x x x x应满应满足:足:足:足: x%5=1 & x%6=5 & x%7=4 & x%11=10x%5=1 & x%6=5 & x%7=4 & x%11=10x%5=1 & x%6=5 & x%7=4 & x%11=10
48、x%5=1 & x%6=5 & x%7=4 & x%11=10 穷举穷举法,法,法,法,对对x x x x从从从从1 1 1 1开开开开场实验场实验【例【例6.15】韩韩信点兵信点兵2024/8/2549/63#include #include main()main() int x;int x; for (x=1; x 5000 ;x+)for (x=1; x 5000 ;x+) if (x%5=1 & x%6=5 & x%7=4 & x%11=10)if (x%5=1 & x%6=5 & x%7=4 & x%11=10) printf(x = %dn, x); printf(x = %dn,
49、 x); 【例【例6.15】韩韩信点兵信点兵“瞎猫碰死耗子瞎猫碰死耗子2024/8/2550/63#include #include main()main() int x;int x; for (x=1; ;x+)for (x=1; ;x+) if (x%5=1 & x%6=5 & x%7=4 & x%11=10)if (x%5=1 & x%6=5 & x%7=4 & x%11=10) printf(x = %dn, x); printf(x = %dn, x); 【例【例6.15】韩韩信点兵信点兵“死循死循环2024/8/2551/63#include #include main()main
50、() int x;int x; for (x=1; ;x+) for (x=1; ;x+) if (x%5=1 & x%6=5 & x%7=4 & x%11=10)if (x%5=1 & x%6=5 & x%7=4 & x%11=10) printf(x = %dn, x); printf(x = %dn, x); goto END;goto END; END: ; END: ; 【例【例6.15】韩韩信点兵信点兵goto2024/8/2552/63#include #include main()main() int x;int x; for (x=1; ;x+) for (x=1; ;x+)
51、 if (x%5=1 & x%6=5 & x%7=4 & x%11=10)if (x%5=1 & x%6=5 & x%7=4 & x%11=10) printf(x = %dn, x); printf(x = %dn, x); break;break; 【例【例6.15】韩韩信点兵信点兵break2024/8/2553/63#include #include #include #include main()main() int x;int x; for (x=1; ;x+) for (x=1; ;x+) if (x%5=1 & x%6=5 & x%7=4 & x%11=10)if (x%5=1
52、 & x%6=5 & x%7=4 & x%11=10) printf(x = %dn, x); printf(x = %dn, x); exit(0);exit(0); 【例【例6.15】韩韩信点兵信点兵break规范范库函数,函数,作用是作用是终止整止整个程序的个程序的执行,行,强强迫前往操作迫前往操作系系统 2024/8/2554/63#include #include main()main() int x; int x; int find = 0; /*int find = 0; /*置找到置找到置找到置找到标标标标志志志志为为为为假假假假*/*/for (x=1; !find ;x+)
53、 for (x=1; !find ;x+) if (x%5=1 & x%6=5 & x%7=4 & x%11=10)if (x%5=1 & x%6=5 & x%7=4 & x%11=10) printf(x = %dn, x); printf(x = %dn, x); find = 1; /*find = 1; /*置找到置找到置找到置找到标标标标志志志志为为为为真真真真*/ */ 【例【例6.15】韩韩信点兵信点兵标标志志变变量量构造明晰的构造明晰的程序程序2024/8/2555/636.6本章本章扩扩展内容展内容 构造化程序构造化程序构造化程序构造化程序设计设计Structured Pro
54、grammingStructured Programming 19651965年,最早由年,最早由年,最早由年,最早由E.W.DijkstraE.W.Dijkstra在一次国在一次国在一次国在一次国际际会会会会议议上提出上提出上提出上提出 19661966年,年,年,年,C.BohmC.Bohm和和和和G.JacopiniG.Jacopini首先首先首先首先证证明了:明了:明了:明了: 只用只用只用只用顺顺序、序、序、序、选择选择、循、循、循、循环环三种根本的控制构培育能三种根本的控制构培育能三种根本的控制构培育能三种根本的控制构培育能实实现现任何任何任何任何单单入口、入口、入口、入口、单单出
55、口的程序出口的程序出口的程序出口的程序 给给构造化程序构造化程序构造化程序构造化程序设计设计奠定了根底奠定了根底奠定了根底奠定了根底 19711971年,年,年,年,IBMIBM公司的公司的公司的公司的MillsMills提出:提出:提出:提出: 程序程序程序程序应该应该只需一个入口和一个出口只需一个入口和一个出口只需一个入口和一个出口只需一个入口和一个出口 进进一步一步一步一步补补充了构造化程序的充了构造化程序的充了构造化程序的充了构造化程序的规规那么那么那么那么2024/8/2556/636.6本章本章扩扩展内容展内容 目前,目前,目前,目前,还还没有一个没有一个没有一个没有一个严厉严厉的
56、定的定的定的定义义 19741974年,年,年,年,D.GriesD.Gries教授将已有的教授将已有的教授将已有的教授将已有的对对构造化程序构造化程序构造化程序构造化程序设计设计的的的的不同解不同解不同解不同解释归纳为释归纳为1313种。种。种。种。 一个比一个比一个比一个比较较流行的定流行的定流行的定流行的定义义是:是:是:是: 构造化程序构造化程序构造化程序构造化程序设计设计是一种是一种是一种是一种进进展程序展程序展程序展程序设计设计的原那么和方的原那么和方的原那么和方的原那么和方法法法法 它防止运用它防止运用它防止运用它防止运用gotogoto语语句句句句 采用采用采用采用“ “自自自
57、自顶顶向下、逐向下、逐向下、逐向下、逐渐渐求精方法求精方法求精方法求精方法进进展程序展程序展程序展程序设计设计 按照按照按照按照这这种原那么和方法种原那么和方法种原那么和方法种原那么和方法设计设计出的程序的特点出的程序的特点出的程序的特点出的程序的特点为为: 构造明晰构造明晰构造明晰构造明晰 容易容易容易容易阅读阅读 容易修正容易修正容易修正容易修正 容易容易容易容易验证验证2024/8/2557/63START_LOOP:START_LOOP:if (fStatusOk) if (fStatusOk) if (fDataAvaiable) if (fDataAvaiable) i = 10;
58、 i = 10; goto MID_LOOP; goto MID_LOOP; else else goto END_LOOP; goto END_LOOP; else else for (i = 0; i 100; i+) for (i = 0; i 100; i+) MID_LOOP:MID_LOOP: / lots of code here / lots of code here goto START_LOOP; goto START_LOOP; END_LOOP:END_LOOP:糟糕的糟糕的goto语句句2024/8/2558/63用用goto语句跳向共同的出口位置句跳向共同的出口位置
59、void Init(void)void Init(void) char *p1 = NULL;char *p1 = NULL;char *p2 = NULL;char *p2 = NULL;char *p3 = NULL;char *p3 = NULL;p1 = (char*)malloc(256);p1 = (char*)malloc(256); if (p1 = NULL)if (p1 = NULL) goto Exit; goto Exit; p2 = (char*)malloc(256);p2 = (char*)malloc(256); if (p2 = NULL)if (p2 = N
60、ULL) goto Exit; goto Exit; p3 = (char*)malloc(256);p3 = (char*)malloc(256); if (p3 = NULL)if (p3 = NULL) goto Exit; goto Exit; /*/*正常正常正常正常处处处处置的代置的代置的代置的代码码码码*/*/Exit:Exit: if (p1 != NULL) if (p1 != NULL) free(p1); free(p1); if (p2 != NULL) if (p2 != NULL) free(p2); free(p2); if (p3 != NULL) if (p3
61、 != NULL) free(p3); free(p3); return; return; 2024/8/2559/63Evil gotos ? Maybe Not凌波微步,未必摔跤凌波微步,未必摔跤 现现代代代代观观念以念以念以念以为为: 混乱根源不在混乱根源不在混乱根源不在混乱根源不在gotogoto语语句,而在句,而在句,而在句,而在语语句句句句标标号号号号 任何程序都可以不用任何程序都可以不用任何程序都可以不用任何程序都可以不用gotogoto语语句就句就句就句就实现实现其功能其功能其功能其功能 但在某些情况下,运用但在某些情况下,运用但在某些情况下,运用但在某些情况下,运用gotog
62、oto语语句可使程序更明句可使程序更明句可使程序更明句可使程序更明晰晰晰晰 两种适宜运用两种适宜运用两种适宜运用两种适宜运用gotogoto语语句的情况句的情况句的情况句的情况 跳向共同的出口位置,跳向共同的出口位置,跳向共同的出口位置,跳向共同的出口位置,进进展退出前的展退出前的展退出前的展退出前的处处置任置任置任置任务务 跳出多重循跳出多重循跳出多重循跳出多重循环环的一条捷径的一条捷径的一条捷径的一条捷径 goto error; goto error; 2024/8/2560/63构造化程序构造化程序设计关注的焦点关注的焦点 不能不能简单地以地以为 防止运用防止运用goto语句的程序句的程
63、序设计方法就是构造方法就是构造化程序化程序设计方法方法 构造化程序构造化程序设计关注的焦点关注的焦点 程序构造的好坏程序构造的好坏 有无有无goto语句,并不是程序构造好坏的句,并不是程序构造好坏的标志志 限制和防止运用限制和防止运用goto语句,只是得到构造化句,只是得到构造化程序的一种手段,而不是目的程序的一种手段,而不是目的2024/8/2561/63构造化程序构造化程序设计的中心思想的中心思想 采用采用采用采用顺顺序、序、序、序、选择选择和循和循和循和循环环三种根本构造作三种根本构造作三种根本构造作三种根本构造作为为程序程序程序程序设计设计的根本的根本的根本的根本单单元元元元 只需一个
64、入口只需一个入口只需一个入口只需一个入口 只需一个出口只需一个出口只需一个出口只需一个出口 无死无死无死无死语语句,即不存在永句,即不存在永句,即不存在永句,即不存在永远远都都都都执执行不到的行不到的行不到的行不到的语语句句句句 无死循无死循无死循无死循环环,即不存在永,即不存在永,即不存在永,即不存在永远远都都都都执执行不完的循行不完的循行不完的循行不完的循环环 采用采用采用采用“自自自自顶顶向下、逐向下、逐向下、逐向下、逐渐渐求精和模求精和模求精和模求精和模块块化的方法化的方法化的方法化的方法进进展展展展构造化程序构造化程序构造化程序构造化程序设计设计 Top-down, Stepwise
65、 refinementTop-down, Stepwise refinementTop-down, Stepwise refinementTop-down, Stepwise refinement 1971 1971 1971 1971年,年,年,年,wirthwirthwirthwirth提出提出提出提出 先全局后部分,先整体后先全局后部分,先整体后先全局后部分,先整体后先全局后部分,先整体后细节细节,先,先,先,先笼统笼统后后后后详细详细2024/8/2562/63运用运用goto语句的原那么句的原那么 主主主主张张少用、慎用,而不是禁用少用、慎用,而不是禁用少用、慎用,而不是禁用少用、慎
66、用,而不是禁用 保保保保证证运用之后,程序依然是运用之后,程序依然是运用之后,程序依然是运用之后,程序依然是单单入口,入口,入口,入口,单单出口出口出口出口 不要运用一个以上的不要运用一个以上的不要运用一个以上的不要运用一个以上的标标号号号号 不要用不要用不要用不要用gotogoto语语句往回跳,要向下跳句往回跳,要向下跳句往回跳,要向下跳句往回跳,要向下跳 不要不要不要不要让让gotogoto语语句制造出永句制造出永句制造出永句制造出永远远不会被不会被不会被不会被执执行的代行的代行的代行的代码码2024/8/2563/63 Questions and answersQuestions and answers