Skip to content

Commit cac76cb

Browse files
author
wolf
committed
chapter05
1 parent 66955be commit cac76cb

File tree

1 file changed

+149
-0
lines changed

1 file changed

+149
-0
lines changed

thinkpython/tex-zh/part/chapter05.tex

Lines changed: 149 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -240,3 +240,152 @@ \section{链式条件}
240240
如此。如果有一个为真,相应的分支就被执行,链式语句也就终止
241241
。尽管可能有多个条件为真,也只有第一个为真的分支被执行。\\
242242

243+
244+
\section{嵌套的条件语句}
245+
\index{nested conditional 嵌套的条件语句}
246+
\index{conditional!nested}
247+
248+
一条条件语句也可以嵌套在另一个语句之中。我们写一个典型的例子:
249+
250+
\beforeverb
251+
\begin{verbatim}
252+
if x == y:
253+
print 'x and y are equal'
254+
else:
255+
if x < y:
256+
print 'x is less than y'
257+
else:
258+
print 'x is greater than y'
259+
\end{verbatim}
260+
\afterverb
261+
外层的条件包两个分支。第一个分支包含一个简单语句。第二个分支包含例外一个
262+
{\tt if}语句,同时,这个{\tt if}语句也有两个分支。这两个简单的分之都是简
263+
单语句,尽管他们本也可能是条件语句。\\
264+
265+
尽管缩进使得代码结构清晰,嵌套语句还是难以快速的理解。一般来说,尽可能的
266+
避免使用嵌套条件语句。\\
267+
268+
逻辑运算符可以简化嵌套条件语句。比如,下面的代码可以只用一条条件语句:
269+
270+
\beforeverb
271+
\begin{verbatim}
272+
if 0 < x:
273+
if x < 10:
274+
print 'x is a positive single-digit number.'
275+
\end{verbatim}
276+
\afterverb
277+
278+
只有当我们“通过”了两个条件时,{\tt print}语句才会被执行,所以,我们可以用{\tt and}运算符达到同样的效果。
279+
280+
\beforeverb
281+
\begin{verbatim}
282+
if 0 < x and x < 10:
283+
print 'x is a positive single-digit number.'
284+
\end{verbatim}
285+
\afterverb
286+
287+
288+
289+
\section{递归}
290+
\label{recusion}
291+
\index{recursion 递归}
292+
293+
294+
函数调用\footnote{译注:台湾的书籍一般翻译为呼叫,这个很形象}另外一个函数是合法的;函数调用他自身也是合法的。很难一眼看出这样做有什么好处\footnote{译者注:我猜,这种情况就像是自己把自己提起来一样~~},但实践证明,
295+
这是程序能做的最具有魔力的事情之一。比如,看下面的函数:
296+
297+
\beforeverb
298+
\begin{verbatim}
299+
def countdown(n):
300+
if n <= 0:
301+
print 'Blastoff!'
302+
else:
303+
print n
304+
countdown(n-1)
305+
\end{verbatim}
306+
\afterverb
307+
308+
如果{\tt n}是非正数,程序输出,“Blastoff!“,否则,输出{\tt n},然后调用
309+
{\tt countdown}函数---也就是它自己---同时把{\tt n-1}当作参数传递给它。
310+
311+
如果我们调用这个函数,究竟发生了什么?
312+
313+
\beforeverb
314+
\begin{verbatim}
315+
>>> countdown(3)
316+
\end{verbatim}
317+
\afterverb
318+
%
319+
{\tt countdown}从{\tt n=3}开始执行,{\tt n}此时大于0,于是输出3,接着
320+
调用自身。。。。。。
321+
322+
\begin{quote}
323+
{\tt countdown}从{\tt n=2}开始执行,{\tt n}此时大于0,于是输出2,接着调用自身。。。。。。
324+
325+
\begin{quote}
326+
{\tt countdown}从{\tt n=1}开始执行,{\tt n}此时大于0,于是输出1,接着调用自身。。。。。。
327+
328+
\begin{quote}
329+
{\tt countdown}从{\tt n=0}开始执行,{\tt n}此时不大于0,输出“Blastoff!"
330+
然后返回。
331+
\end{quote}
332+
333+
接受{\tt n=1}的{\tt countdown}返回。
334+
\edn{quote}
335+
336+
接受{\tt n=2}的{\tt countdown}返回。
337+
\end{quote}
338+
339+
接受{\tt n=2}的{\tt countdown}返回。
340+
\end{quote}
341+
342+
{\tt countdown}接受{\tt n=3}的函数返回。
343+
344+
然后,我们就会到\verb"__main__"里了。整个输出如下:
345+
346+
\beforeverb
347+
\begin{verbatim}
348+
3
349+
2
350+
1
351+
Blastoff!
352+
\end{verbatim}
353+
\afterverb
354+
355+
调用自身的函数称作递归函数;调用的过程叫做递归。
356+
357+
\index{recursion 递归}
358+
\index{function!recursive}
359+
360+
另外一个例子,我们写一个打印一个字符串{\tt n}次的函数。
361+
362+
\beforeverb
363+
\begin{verbatim}
364+
def print_n(s, n):
365+
if n <= 0:
366+
return
367+
print s
368+
print_n(s, n-1)
369+
\end{verbatim}
370+
\afterverb
371+
372+
如果{\tt n <= 0},{\tt return}语句退出函数。执行流立刻返回到调用者,
373+
剩余的部分就不再被执行了。
374+
375+
\index{return statement return语句}
376+
\index{statement!return}
377+
378+
函数的剩余部分和{\tt countdown}还书相似:如果{\tt n}大于0,输出{\tt s},然后调用自身显示{\tt s} $n-1$次。所以,输出的行数是{\tt 1 + (n-1)},
379+
也就是{\tt n}次。\\
380+
381+
这样简单的例子,其实可以很容易用一个{\tt for}循环来实现。但我们以后将会看
382+
到很难写成{\tt for}循环形式,但是很容易用递归实现的例子,我们现在就
383+
开始认识递归是有好处的。
384+
385+
{\section{递归函数的堆栈图}
386+
\index{stack diagram 堆栈图}
387+
\index{function frame 函数图}
388+
\index{frame 图}
389+
390+
391+

0 commit comments

Comments
 (0)