The best way to learn a programming language is to write a lot of code and read a lot of code.
我们已经看到了,在循环体(也就是代码块)中可以放入其他代码,这些代码本身也可以有自己的代码块。如果查看第1篇中的猜数程序,可以看到:
外层浅灰色的块是一个while循环块,深灰色的块是这个while循环块中的if和elif块。
还可以把一个循环放在另一个循环中。这些循环就叫嵌套循环。
嵌套循环
还记得第8篇“动手试一试”中你写的乘法表程序吗?如果不考虑用户输入部分,代码会是这样:
如果想一次打印3个乘法表呢?这种事情正是嵌套循环最擅长的。嵌套循环就是一个循环出现在另一个循环里。对于外循环的每次迭代,内循环都要完成它的所有迭代。
要打印3个乘法表,只需要把原来的循环(打印一个乘法表)包含在一个外循环中(运行3次)。这样,程序就会打印3个乘法表而不只是一个。代码清单如下:
注意必须将内循环缩进,而且print语句距外部for循环开始位置还要多加4个空格。这个程序会分别打印5、6、7的乘法表,每个表分别从1乘到10:
可变循环
固定的数(比如range()函数中使用的数)也称为常数。如果在一个for循环的range()函数中使用常数,程序运行时循环总会运行相同的次数。在这种情况下,我们称循环次数是硬编码,因为它在你的代码中被定义了,而且永远不会改变。这往往不是我们真正想要的。
有时我们希望循环次数由用户来决定,或者由程序的另一部分决定。对于这种情况,我们就需要一个变量。
下面先给出一个使用可变循环的简单示例程序:
运行结果如下:
可变嵌套循环
现在来尝试一个可变嵌套循环。这就是将上述的嵌套循环和可变循环进行结合,我们来看看以下一个例子。
运行这个程序来看它的作用,你会看到类似这样的结果:
前两行询问用户想要多少行,以及每行希望有多少个星号。程序使用变量numLine和numStars记住这些答案。接下来有两个循环:
内循环(for j in range(numStars):)打印每个星号,对每一行上的每个星号分别运行一次;
外循环(for i in range(numLines):)对每行星号分别运行一次。
需要用第二个print命令开始新的一行星号。如果没有这个命令,由于第一个print语句中有逗号,所有星号都会打印到同一行上。
另外还有种“嵌套嵌套循环”(或双重嵌套循环),就像如下代码:
会得到下面的输出:
我们称这个循环嵌套“深度为3”。
一个更复杂的星号块
我们再来看看下面这个代码:
输出如下:
外循环的循环变量用来为内循环设置范围。所以每个星号块不再有相同的行数,而且每一行也不再有相同的星号数,每次循环时行数和星号数都不同。
你希望循环嵌套多深,就可以有多深。要明白这样的嵌套循环会让人心疼,所以有时打印出循环变量的值会很有帮助,如下列代码所示。
以下是这个程序的输出:
在很多情况下,而不只限于在循环中,打印变量的值都会对你很有帮助。这也是最常用的高度方法之一。
应用实例
下面假设你要开个热狗店,你想做个菜单表,用数字显示如何订购热狗、面包、番茄酱、芥末酱和洋葱的所有可能的组合。所以我们需要得出总共多少种可能的组合。
考虑这个问题的一种方法就是使用决策树。下面的图显示了这个热狗问题的决策树。
每个决策点都有两种选择,是(Y)或者否(N)。这棵树的每一条不同的路径分别描述了热狗各部分的不同的组合。这里突出显示的路径是这样选择的:热狗选择Y,面包选择N,芥末酱选择Y,番茄酱选择Y。
现在我们使用嵌套循环来列出所有组合,也就是这棵决策树的所有路径。由于这里有5个决策点,所以在我们的决策树中有5层,相应地,在程序中就会有5个嵌套循环。(上图只显示了决策树的前4层)
我们打开代码清单11-6:
看到这些循环是如何一个套一个了吗?这正是嵌套循环,即一个循环放在另一个循环中。
外循环(热狗循环)运行两次。
对热狗循环的每一次迭代,小面包循环运行两次,所以它会运行2×2=4次。
对小面包循环的每一次迭代,番茄酱循环运行两次,所以它会运行2×2×2=8次。
依此类推。
最内层循环(嵌套最深的循环,也就是洋葱循环)会运行2×2×2×2×2=32次。这就涵盖了所有可能的组合。因此共有32种可能的组合。
如果运行上述代码清单,会得到下面的结果:
这5个嵌套循环可以得到热狗、小面包、番茄酱、芥末酱和洋葱的所有可能的组合。
在上述的代码清单中,我们使用了制表符来实现对齐,也就是符号“\t”。打印格式我们会在后面讨论到,现在你只需要记住这个制表符就可以了。这里还使用了一个名为count的变量对各个组合编号。当然,现在如果仔细看这32个组合,你会发现有些组合并没有实际意义。如那些没有小面包,但有番茄酱和芥末酱,这样的热狗肯定会弄得一团糟。
现在我们可以知道,嵌套循环其实最擅长的工作就是得出一系列决定的所有可能的排列和组合。
END
回顾
嵌套循环
可变循环
决策树
测试题
Python中如何建立可变循环?
Python中如何建立嵌套循环?
下面的代码总共会打印多少星号:
第3题中的代码会得到什么输出?
如果一个决策树有4层,每层有两个选择,共有多少种可能的选择以(决策树有多少条路径)?
动手试一试
以下是第8篇中创建的倒计时定时器程序:
使用一个可变循环修改程序。这个程序要询问用户向下计数应当从哪里开始,比如:
根据第1题写的程序,让它除了打印各个数之外还要打印一行星号,如下:
(提示:可能需要使用一个嵌套循环。)
领取专属 10元无门槛券
私享最新 技术干货