-
-
Notifications
You must be signed in to change notification settings - Fork 214
/
Copy pathcontrolflow.html
1129 lines (1066 loc) · 134 KB
/
controlflow.html
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
217
218
219
220
221
222
223
224
225
226
227
228
229
230
231
232
233
234
235
236
237
238
239
240
241
242
243
244
245
246
247
248
249
250
251
252
253
254
255
256
257
258
259
260
261
262
263
264
265
266
267
268
269
270
271
272
273
274
275
276
277
278
279
280
281
282
283
284
285
286
287
288
289
290
291
292
293
294
295
296
297
298
299
300
301
302
303
304
305
306
307
308
309
310
311
312
313
314
315
316
317
318
319
320
321
322
323
324
325
326
327
328
329
330
331
332
333
334
335
336
337
338
339
340
341
342
343
344
345
346
347
348
349
350
351
352
353
354
355
356
357
358
359
360
361
362
363
364
365
366
367
368
369
370
371
372
373
374
375
376
377
378
379
380
381
382
383
384
385
386
387
388
389
390
391
392
393
394
395
396
397
398
399
400
401
402
403
404
405
406
407
408
409
410
411
412
413
414
415
416
417
418
419
420
421
422
423
424
425
426
427
428
429
430
431
432
433
434
435
436
437
438
439
440
441
442
443
444
445
446
447
448
449
450
451
452
453
454
455
456
457
458
459
460
461
462
463
464
465
466
467
468
469
470
471
472
473
474
475
476
477
478
479
480
481
482
483
484
485
486
487
488
489
490
491
492
493
494
495
496
497
498
499
500
501
502
503
504
505
506
507
508
509
510
511
512
513
514
515
516
517
518
519
520
521
522
523
524
525
526
527
528
529
530
531
532
533
534
535
536
537
538
539
540
541
542
543
544
545
546
547
548
549
550
551
552
553
554
555
556
557
558
559
560
561
562
563
564
565
566
567
568
569
570
571
572
573
574
575
576
577
578
579
580
581
582
583
584
585
586
587
588
589
590
591
592
593
594
595
596
597
598
599
600
601
602
603
604
605
606
607
608
609
610
611
612
613
614
615
616
617
618
619
620
621
622
623
624
625
626
627
628
629
630
631
632
633
634
635
636
637
638
639
640
641
642
643
644
645
646
647
648
649
650
651
652
653
654
655
656
657
658
659
660
661
662
663
664
665
666
667
668
669
670
671
672
673
674
675
676
677
678
679
680
681
682
683
684
685
686
687
688
689
690
691
692
693
694
695
696
697
698
699
700
701
702
703
704
705
706
707
708
709
710
711
712
713
714
715
716
717
718
719
720
721
722
723
724
725
726
727
728
729
730
731
732
733
734
735
736
737
738
739
740
741
742
743
744
745
746
747
748
749
750
751
752
753
754
755
756
757
758
759
760
761
762
763
764
765
766
767
768
769
770
771
772
773
774
775
776
777
778
779
780
781
782
783
784
785
786
787
788
789
790
791
792
793
794
795
796
797
798
799
800
801
802
803
804
805
806
807
808
809
810
811
812
813
814
815
816
817
818
819
820
821
822
823
824
825
826
827
828
829
830
831
832
833
834
835
836
837
838
839
840
841
842
843
844
845
846
847
848
849
850
851
852
853
854
855
856
857
858
859
860
861
862
863
864
865
866
867
868
869
870
871
872
873
874
875
876
877
878
879
880
881
882
883
884
885
886
887
888
889
890
891
892
893
894
895
896
897
898
899
900
901
902
903
904
905
906
907
908
909
910
911
912
913
914
915
916
917
918
919
920
921
922
923
924
925
926
927
928
929
930
931
932
933
934
935
936
937
938
939
940
941
942
943
944
945
946
947
948
949
950
951
952
953
954
955
956
957
958
959
960
961
962
963
964
965
966
967
968
969
970
971
972
973
974
975
976
977
978
979
980
981
982
983
984
985
986
987
988
989
990
991
992
993
994
995
996
997
998
999
1000
<!DOCTYPE html>
<html lang="zh-TW" data-content_root="../">
<head>
<meta charset="utf-8" />
<meta name="viewport" content="width=device-width, initial-scale=1.0" /><meta name="viewport" content="width=device-width, initial-scale=1" />
<title>4. 深入了解流程控制 — Python 3.13.2 說明文件</title><meta name="viewport" content="width=device-width, initial-scale=1.0">
<link rel="stylesheet" type="text/css" href="../_static/pygments.css?v=b86133f3" />
<link rel="stylesheet" type="text/css" href="../_static/pydoctheme.css?v=23252803" />
<link id="pygments_dark_css" media="(prefers-color-scheme: dark)" rel="stylesheet" type="text/css" href="../_static/pygments_dark.css?v=5349f25f" />
<script src="../_static/documentation_options.js?v=9a295789"></script>
<script src="../_static/doctools.js?v=9bcbadda"></script>
<script src="../_static/sphinx_highlight.js?v=dc90522c"></script>
<script src="../_static/translations.js?v=cbf116e0"></script>
<script src="../_static/sidebar.js"></script>
<link rel="search" type="application/opensearchdescription+xml"
title="在 Python 3.13.2 說明文件 中搜尋"
href="../_static/opensearch.xml"/>
<link rel="author" title="關於這些文件" href="../about.html" />
<link rel="index" title="索引" href="../genindex.html" />
<link rel="search" title="搜尋" href="../search.html" />
<link rel="copyright" title="版權" href="../copyright.html" />
<link rel="next" title="5. 資料結構" href="datastructures.html" />
<link rel="prev" title="3. 一個非正式的 Python 簡介" href="introduction.html" />
<link rel="canonical" href="https://docs.python.org/3/tutorial/controlflow.html" />
<style>
@media only screen {
table.full-width-table {
width: 100%;
}
}
</style>
<link rel="stylesheet" href="../_static/pydoctheme_dark.css" media="(prefers-color-scheme: dark)" id="pydoctheme_dark_css">
<link rel="shortcut icon" type="image/png" href="../_static/py.svg" />
<script type="text/javascript" src="../_static/copybutton.js"></script>
<script type="text/javascript" src="../_static/menu.js"></script>
<script type="text/javascript" src="../_static/search-focus.js"></script>
<script type="text/javascript" src="../_static/themetoggle.js"></script>
<script type="text/javascript" src="../_static/rtd_switcher.js"></script>
<meta name="readthedocs-addons-api-version" content="1">
</head>
<body>
<div class="mobile-nav">
<input type="checkbox" id="menuToggler" class="toggler__input" aria-controls="navigation"
aria-pressed="false" aria-expanded="false" role="button" aria-label="Menu" />
<nav class="nav-content" role="navigation">
<label for="menuToggler" class="toggler__label">
<span></span>
</label>
<span class="nav-items-wrapper">
<a href="https://www.python.org/" class="nav-logo">
<img src="../_static/py.svg" alt="Python logo"/>
</a>
<span class="version_switcher_placeholder"></span>
<form role="search" class="search" action="../search.html" method="get">
<svg xmlns="http://www.w3.org/2000/svg" width="20" height="20" viewBox="0 0 24 24" class="search-icon">
<path fill-rule="nonzero" fill="currentColor" d="M15.5 14h-.79l-.28-.27a6.5 6.5 0 001.48-5.34c-.47-2.78-2.79-5-5.59-5.34a6.505 6.505 0 00-7.27 7.27c.34 2.8 2.56 5.12 5.34 5.59a6.5 6.5 0 005.34-1.48l.27.28v.79l4.25 4.25c.41.41 1.08.41 1.49 0 .41-.41.41-1.08 0-1.49L15.5 14zm-6 0C7.01 14 5 11.99 5 9.5S7.01 5 9.5 5 14 7.01 14 9.5 11.99 14 9.5 14z"></path>
</svg>
<input placeholder="快速搜尋" aria-label="快速搜尋" type="search" name="q" />
<input type="submit" value="前往"/>
</form>
</span>
</nav>
<div class="menu-wrapper">
<nav class="menu" role="navigation" aria-label="main navigation">
<div class="language_switcher_placeholder"></div>
<label class="theme-selector-label">
Theme
<select class="theme-selector" oninput="activateTheme(this.value)">
<option value="auto" selected>Auto</option>
<option value="light">Light</option>
<option value="dark">Dark</option>
</select>
</label>
<div>
<h3><a href="../contents.html">目錄</a></h3>
<ul>
<li><a class="reference internal" href="#">4. 深入了解流程控制</a><ul>
<li><a class="reference internal" href="#if-statements">4.1. <code class="xref std std-keyword docutils literal notranslate"><span class="pre">if</span></code> 陳述式</a></li>
<li><a class="reference internal" href="#for-statements">4.2. <code class="xref std std-keyword docutils literal notranslate"><span class="pre">for</span></code> 陳述式</a></li>
<li><a class="reference internal" href="#the-range-function">4.3. <code class="xref py py-func docutils literal notranslate"><span class="pre">range()</span></code> 函式</a></li>
<li><a class="reference internal" href="#break-and-continue-statements">4.4. <code class="xref std std-keyword docutils literal notranslate"><span class="pre">break</span></code> 和 <code class="xref std std-keyword docutils literal notranslate"><span class="pre">continue</span></code> 陳述式</a></li>
<li><a class="reference internal" href="#else-clauses-on-loops">4.5. 迴圈的 <code class="xref std std-keyword docutils literal notranslate"><span class="pre">else</span></code> 子句</a></li>
<li><a class="reference internal" href="#pass-statements">4.6. <code class="xref std std-keyword docutils literal notranslate"><span class="pre">pass</span></code> 陳述式</a></li>
<li><a class="reference internal" href="#match-statements">4.7. <code class="xref std std-keyword docutils literal notranslate"><span class="pre">match</span></code> 陳述式</a></li>
<li><a class="reference internal" href="#defining-functions">4.8. 定義函式 (function)</a></li>
<li><a class="reference internal" href="#more-on-defining-functions">4.9. 深入了解函式定義</a><ul>
<li><a class="reference internal" href="#default-argument-values">4.9.1. 預設引數值</a></li>
<li><a class="reference internal" href="#keyword-arguments">4.9.2. 關鍵字引數</a></li>
<li><a class="reference internal" href="#special-parameters">4.9.3. 特殊參數</a><ul>
<li><a class="reference internal" href="#positional-or-keyword-arguments">4.9.3.1. 位置或關鍵字引數 (Positional-or-Keyword Arguments)</a></li>
<li><a class="reference internal" href="#positional-only-parameters">4.9.3.2. 僅限位置參數 (Positional-Only Parameters)</a></li>
<li><a class="reference internal" href="#keyword-only-arguments">4.9.3.3. 僅限關鍵字引數 (Keyword-Only Arguments)</a></li>
<li><a class="reference internal" href="#function-examples">4.9.3.4. 函式範例</a></li>
<li><a class="reference internal" href="#recap">4.9.3.5. 回顧</a></li>
</ul>
</li>
<li><a class="reference internal" href="#arbitrary-argument-lists">4.9.4. 任意引數列表 (Arbitrary Argument Lists)</a></li>
<li><a class="reference internal" href="#unpacking-argument-lists">4.9.5. 拆解引數列表(Unpacking Argument Lists)</a></li>
<li><a class="reference internal" href="#lambda-expressions">4.9.6. Lambda 運算式</a></li>
<li><a class="reference internal" href="#documentation-strings">4.9.7. 說明文件字串 (Documentation Strings)</a></li>
<li><a class="reference internal" href="#function-annotations">4.9.8. 函式註釋 (Function Annotations)</a></li>
</ul>
</li>
<li><a class="reference internal" href="#intermezzo-coding-style">4.10. 間奏曲:程式碼風格 (Coding Style)</a></li>
</ul>
</li>
</ul>
</div>
<div>
<h4>上個主題</h4>
<p class="topless"><a href="introduction.html"
title="上一章"><span class="section-number">3. </span>一個非正式的 Python 簡介</a></p>
</div>
<div>
<h4>下個主題</h4>
<p class="topless"><a href="datastructures.html"
title="下一章"><span class="section-number">5. </span>資料結構</a></p>
</div>
<div role="note" aria-label="source link">
<h3>此頁面</h3>
<ul class="this-page-menu">
<li><a href="../bugs.html">回報錯誤</a></li>
<li>
<a href="https://github.com/python/cpython/blob/main/Doc/tutorial/controlflow.rst"
rel="nofollow">顯示原始碼
</a>
</li>
</ul>
</div>
</nav>
</div>
</div>
<div class="related" role="navigation" aria-label="Related">
<h3>瀏覽</h3>
<ul>
<li class="right" style="margin-right: 10px">
<a href="../genindex.html" title="總索引"
accesskey="I">索引</a></li>
<li class="right" >
<a href="../py-modindex.html" title="Python 模組索引"
>模組</a> |</li>
<li class="right" >
<a href="datastructures.html" title="5. 資料結構"
accesskey="N">下一頁</a> |</li>
<li class="right" >
<a href="introduction.html" title="3. 一個非正式的 Python 簡介"
accesskey="P">上一頁</a> |</li>
<li><img src="../_static/py.svg" alt="Python logo" style="vertical-align: middle; margin-top: -1px"/></li>
<li><a href="https://www.python.org/">Python</a> »</li>
<li class="switchers">
<div class="language_switcher_placeholder"></div>
<div class="version_switcher_placeholder"></div>
</li>
<li>
</li>
<li id="cpython-language-and-version">
<a href="../index.html">3.13.2 Documentation</a> »
</li>
<li class="nav-item nav-item-1"><a href="index.html" accesskey="U">Python 教學</a> »</li>
<li class="nav-item nav-item-this"><a href=""><span class="section-number">4. </span>深入了解流程控制</a></li>
<li class="right">
<div class="inline-search" role="search">
<form class="inline-search" action="../search.html" method="get">
<input placeholder="快速搜尋" aria-label="快速搜尋" type="search" name="q" id="search-box" />
<input type="submit" value="前往" />
</form>
</div>
|
</li>
<li class="right">
<label class="theme-selector-label">
Theme
<select class="theme-selector" oninput="activateTheme(this.value)">
<option value="auto" selected>Auto</option>
<option value="light">Light</option>
<option value="dark">Dark</option>
</select>
</label> |</li>
</ul>
</div>
<div class="document">
<div class="documentwrapper">
<div class="bodywrapper">
<div class="body" role="main">
<section id="more-control-flow-tools">
<span id="tut-morecontrol"></span><h1><span class="section-number">4. </span>深入了解流程控制<a class="headerlink" href="#more-control-flow-tools" title="連結到這個標頭">¶</a></h1>
<p>除了剛才介紹的 <a class="reference internal" href="../reference/compound_stmts.html#while"><code class="xref std std-keyword docutils literal notranslate"><span class="pre">while</span></code></a>,這章節還會介紹一些 Python 的陳述式語法。</p>
<section id="if-statements">
<span id="tut-if"></span><h2><span class="section-number">4.1. </span><code class="xref std std-keyword docutils literal notranslate"><span class="pre">if</span></code> 陳述式<a class="headerlink" href="#if-statements" title="連結到這個標頭">¶</a></h2>
<p>或許最常見的陳述式種類就是 <a class="reference internal" href="../reference/compound_stmts.html#if"><code class="xref std std-keyword docutils literal notranslate"><span class="pre">if</span></code></a> 了。舉例來說:</p>
<div class="highlight-python3 notranslate"><div class="highlight"><pre><span></span><span class="gp">>>> </span><span class="n">x</span> <span class="o">=</span> <span class="nb">int</span><span class="p">(</span><span class="nb">input</span><span class="p">(</span><span class="s2">"Please enter an integer: "</span><span class="p">))</span>
<span class="go">Please enter an integer: 42</span>
<span class="gp">>>> </span><span class="k">if</span> <span class="n">x</span> <span class="o"><</span> <span class="mi">0</span><span class="p">:</span>
<span class="gp">... </span> <span class="n">x</span> <span class="o">=</span> <span class="mi">0</span>
<span class="gp">... </span> <span class="nb">print</span><span class="p">(</span><span class="s1">'Negative changed to zero'</span><span class="p">)</span>
<span class="gp">... </span><span class="k">elif</span> <span class="n">x</span> <span class="o">==</span> <span class="mi">0</span><span class="p">:</span>
<span class="gp">... </span> <span class="nb">print</span><span class="p">(</span><span class="s1">'Zero'</span><span class="p">)</span>
<span class="gp">... </span><span class="k">elif</span> <span class="n">x</span> <span class="o">==</span> <span class="mi">1</span><span class="p">:</span>
<span class="gp">... </span> <span class="nb">print</span><span class="p">(</span><span class="s1">'Single'</span><span class="p">)</span>
<span class="gp">... </span><span class="k">else</span><span class="p">:</span>
<span class="gp">... </span> <span class="nb">print</span><span class="p">(</span><span class="s1">'More'</span><span class="p">)</span>
<span class="gp">...</span>
<span class="go">More</span>
</pre></div>
</div>
<p>在陳述式中,可以沒有或有許多個 <a class="reference internal" href="../reference/compound_stmts.html#elif"><code class="xref std std-keyword docutils literal notranslate"><span class="pre">elif</span></code></a> 敘述,且 <a class="reference internal" href="../reference/compound_stmts.html#else"><code class="xref std std-keyword docutils literal notranslate"><span class="pre">else</span></code></a> 敘述並不是必要的。關鍵字 <code class="xref std std-keyword docutils literal notranslate"><span class="pre">elif</span></code> 是「else if」的縮寫,用來避免過多的縮排。一個 <code class="xref std std-keyword docutils literal notranslate"><span class="pre">if</span></code> ... <code class="xref std std-keyword docutils literal notranslate"><span class="pre">elif</span></code> ... <code class="xref std std-keyword docutils literal notranslate"><span class="pre">elif</span></code> ... 序列可以用來替代其他程式語言中的 <code class="docutils literal notranslate"><span class="pre">switch</span></code> 或 <code class="docutils literal notranslate"><span class="pre">case</span></code> 陳述式。</p>
<p>如果你要將同一個值與多個常數進行比較,或者檢查特定的型別或屬性,你可能會發現 <code class="xref std std-keyword docutils literal notranslate"><span class="pre">match</span></code> 陳述式也很有用。更多的細節,請參閱 <a class="reference internal" href="#tut-match"><span class="std std-ref">match 陳述式</span></a>。</p>
</section>
<section id="for-statements">
<span id="tut-for"></span><h2><span class="section-number">4.2. </span><code class="xref std std-keyword docutils literal notranslate"><span class="pre">for</span></code> 陳述式<a class="headerlink" href="#for-statements" title="連結到這個標頭">¶</a></h2>
<p id="index-0">在 Python 中的 <a class="reference internal" href="../reference/compound_stmts.html#for"><code class="xref std std-keyword docutils literal notranslate"><span class="pre">for</span></code></a> 陳述式有點不同於在 C 或 Pascal 中的慣用方式。相較於只能疊代 (iterate) 一個等差數列(如 Pascal),或給予使用者定義疊代步驟與終止條件(如 C),Python 的 <code class="xref std std-keyword docutils literal notranslate"><span class="pre">for</span></code> 陳述式疊代任何序列(list 或者字串)的元素,順序與它們出現在序列中的順序相同。例如(無意雙關):</p>
<div class="highlight-python3 notranslate"><div class="highlight"><pre><span></span><span class="gp">>>> </span><span class="c1"># Measure some strings:</span>
<span class="gp">>>> </span><span class="n">words</span> <span class="o">=</span> <span class="p">[</span><span class="s1">'cat'</span><span class="p">,</span> <span class="s1">'window'</span><span class="p">,</span> <span class="s1">'defenestrate'</span><span class="p">]</span>
<span class="gp">>>> </span><span class="k">for</span> <span class="n">w</span> <span class="ow">in</span> <span class="n">words</span><span class="p">:</span>
<span class="gp">... </span> <span class="nb">print</span><span class="p">(</span><span class="n">w</span><span class="p">,</span> <span class="nb">len</span><span class="p">(</span><span class="n">w</span><span class="p">))</span>
<span class="gp">...</span>
<span class="go">cat 3</span>
<span class="go">window 6</span>
<span class="go">defenestrate 12</span>
</pre></div>
</div>
<p>在疊代一個集合的同時修改該集合的內容,很難獲取想要的結果。比較直觀的替代方式,是疊代該集合的副本,或建立一個新的集合:</p>
<div class="highlight-python3 notranslate"><div class="highlight"><pre><span></span><span class="c1"># Create a sample collection</span>
<span class="n">users</span> <span class="o">=</span> <span class="p">{</span><span class="s1">'Hans'</span><span class="p">:</span> <span class="s1">'active'</span><span class="p">,</span> <span class="s1">'Éléonore'</span><span class="p">:</span> <span class="s1">'inactive'</span><span class="p">,</span> <span class="s1">'景太郎'</span><span class="p">:</span> <span class="s1">'active'</span><span class="p">}</span>
<span class="c1"># Strategy: Iterate over a copy</span>
<span class="k">for</span> <span class="n">user</span><span class="p">,</span> <span class="n">status</span> <span class="ow">in</span> <span class="n">users</span><span class="o">.</span><span class="n">copy</span><span class="p">()</span><span class="o">.</span><span class="n">items</span><span class="p">():</span>
<span class="k">if</span> <span class="n">status</span> <span class="o">==</span> <span class="s1">'inactive'</span><span class="p">:</span>
<span class="k">del</span> <span class="n">users</span><span class="p">[</span><span class="n">user</span><span class="p">]</span>
<span class="c1"># Strategy: Create a new collection</span>
<span class="n">active_users</span> <span class="o">=</span> <span class="p">{}</span>
<span class="k">for</span> <span class="n">user</span><span class="p">,</span> <span class="n">status</span> <span class="ow">in</span> <span class="n">users</span><span class="o">.</span><span class="n">items</span><span class="p">():</span>
<span class="k">if</span> <span class="n">status</span> <span class="o">==</span> <span class="s1">'active'</span><span class="p">:</span>
<span class="n">active_users</span><span class="p">[</span><span class="n">user</span><span class="p">]</span> <span class="o">=</span> <span class="n">status</span>
</pre></div>
</div>
</section>
<section id="the-range-function">
<span id="tut-range"></span><h2><span class="section-number">4.3. </span><a class="reference internal" href="../library/stdtypes.html#range" title="range"><code class="xref py py-func docutils literal notranslate"><span class="pre">range()</span></code></a> 函式<a class="headerlink" href="#the-range-function" title="連結到這個標頭">¶</a></h2>
<p>如果你需要疊代一個數列的話,使用內建 <a class="reference internal" href="../library/stdtypes.html#range" title="range"><code class="xref py py-func docutils literal notranslate"><span class="pre">range()</span></code></a> 函式就很方便。它可以生成一等差數列:</p>
<div class="highlight-python3 notranslate"><div class="highlight"><pre><span></span><span class="gp">>>> </span><span class="k">for</span> <span class="n">i</span> <span class="ow">in</span> <span class="nb">range</span><span class="p">(</span><span class="mi">5</span><span class="p">):</span>
<span class="gp">... </span> <span class="nb">print</span><span class="p">(</span><span class="n">i</span><span class="p">)</span>
<span class="gp">...</span>
<span class="go">0</span>
<span class="go">1</span>
<span class="go">2</span>
<span class="go">3</span>
<span class="go">4</span>
</pre></div>
</div>
<p>給定的結束值永遠不會出現在生成的序列中;<code class="docutils literal notranslate"><span class="pre">range(10)</span></code> 生成的 10 個數值,即對應存取一個長度為 10 的序列內每一個項目的索引值。也可以讓 range 從其他數值開始計數,或者給定不同的公差(甚至為負;有時稱之為 step):</p>
<div class="highlight-python3 notranslate"><div class="highlight"><pre><span></span><span class="gp">>>> </span><span class="nb">list</span><span class="p">(</span><span class="nb">range</span><span class="p">(</span><span class="mi">5</span><span class="p">,</span> <span class="mi">10</span><span class="p">))</span>
<span class="go">[5, 6, 7, 8, 9]</span>
<span class="gp">>>> </span><span class="nb">list</span><span class="p">(</span><span class="nb">range</span><span class="p">(</span><span class="mi">0</span><span class="p">,</span> <span class="mi">10</span><span class="p">,</span> <span class="mi">3</span><span class="p">))</span>
<span class="go">[0, 3, 6, 9]</span>
<span class="gp">>>> </span><span class="nb">list</span><span class="p">(</span><span class="nb">range</span><span class="p">(</span><span class="o">-</span><span class="mi">10</span><span class="p">,</span> <span class="o">-</span><span class="mi">100</span><span class="p">,</span> <span class="o">-</span><span class="mi">30</span><span class="p">))</span>
<span class="go">[-10, -40, -70]</span>
</pre></div>
</div>
<p>欲疊代一個序列的索引值,你可以搭配使用 <a class="reference internal" href="../library/stdtypes.html#range" title="range"><code class="xref py py-func docutils literal notranslate"><span class="pre">range()</span></code></a> 和 <a class="reference internal" href="../library/functions.html#len" title="len"><code class="xref py py-func docutils literal notranslate"><span class="pre">len()</span></code></a> 如下:</p>
<div class="highlight-python3 notranslate"><div class="highlight"><pre><span></span><span class="gp">>>> </span><span class="n">a</span> <span class="o">=</span> <span class="p">[</span><span class="s1">'Mary'</span><span class="p">,</span> <span class="s1">'had'</span><span class="p">,</span> <span class="s1">'a'</span><span class="p">,</span> <span class="s1">'little'</span><span class="p">,</span> <span class="s1">'lamb'</span><span class="p">]</span>
<span class="gp">>>> </span><span class="k">for</span> <span class="n">i</span> <span class="ow">in</span> <span class="nb">range</span><span class="p">(</span><span class="nb">len</span><span class="p">(</span><span class="n">a</span><span class="p">)):</span>
<span class="gp">... </span> <span class="nb">print</span><span class="p">(</span><span class="n">i</span><span class="p">,</span> <span class="n">a</span><span class="p">[</span><span class="n">i</span><span class="p">])</span>
<span class="gp">...</span>
<span class="go">0 Mary</span>
<span class="go">1 had</span>
<span class="go">2 a</span>
<span class="go">3 little</span>
<span class="go">4 lamb</span>
</pre></div>
</div>
<p>然而,在多數的情況,使用 <a class="reference internal" href="../library/functions.html#enumerate" title="enumerate"><code class="xref py py-func docutils literal notranslate"><span class="pre">enumerate()</span></code></a> 函式將更為方便,詳見<a class="reference internal" href="datastructures.html#tut-loopidioms"><span class="std std-ref">迴圈技巧</span></a>。</p>
<p>如果直接印出一個 range 則會出現奇怪的輸出:</p>
<div class="highlight-python3 notranslate"><div class="highlight"><pre><span></span><span class="gp">>>> </span><span class="nb">range</span><span class="p">(</span><span class="mi">10</span><span class="p">)</span>
<span class="go">range(0, 10)</span>
</pre></div>
</div>
<p>在很多情況下,由 <a class="reference internal" href="../library/stdtypes.html#range" title="range"><code class="xref py py-func docutils literal notranslate"><span class="pre">range()</span></code></a> 回傳的物件表現得像是一個 list(串列)一樣,但實際上它並不是。它是一個在疊代時能夠回傳所要求的序列中所有項目的物件,但它不會真正建出這個序列的 list,以節省空間。</p>
<p>我們稱這樣的物件為 <a class="reference internal" href="../glossary.html#term-iterable"><span class="xref std std-term">iterable</span></a>(可疊代物件),意即能作為函式及架構中可以一直獲取項目直到取盡的對象。我們已經了解 <a class="reference internal" href="../reference/compound_stmts.html#for"><code class="xref std std-keyword docutils literal notranslate"><span class="pre">for</span></code></a> 陳述式就是如此的架構,另一個使用 iterable 的函式範例是 <a class="reference internal" href="../library/functions.html#sum" title="sum"><code class="xref py py-func docutils literal notranslate"><span class="pre">sum()</span></code></a>:</p>
<div class="highlight-python3 notranslate"><div class="highlight"><pre><span></span><span class="gp">>>> </span><span class="nb">sum</span><span class="p">(</span><span class="nb">range</span><span class="p">(</span><span class="mi">4</span><span class="p">))</span> <span class="c1"># 0 + 1 + 2 + 3</span>
<span class="go">6</span>
</pre></div>
</div>
<p>待會我們可以看到更多回傳 iterable 和使用 iterable 為引數的函式。在<a class="reference internal" href="datastructures.html#tut-structures"><span class="std std-ref">資料結構</span></a>章節中,我們會討論更多關於 <a class="reference internal" href="../library/stdtypes.html#list" title="list"><code class="xref py py-func docutils literal notranslate"><span class="pre">list()</span></code></a> 的細節。</p>
</section>
<section id="break-and-continue-statements">
<span id="tut-break"></span><h2><span class="section-number">4.4. </span><code class="xref std std-keyword docutils literal notranslate"><span class="pre">break</span></code> 和 <code class="xref std std-keyword docutils literal notranslate"><span class="pre">continue</span></code> 陳述式<a class="headerlink" href="#break-and-continue-statements" title="連結到這個標頭">¶</a></h2>
<p><a class="reference internal" href="../reference/simple_stmts.html#break"><code class="xref std std-keyword docutils literal notranslate"><span class="pre">break</span></code></a> 陳述式,終止包含它的最內部 <a class="reference internal" href="../reference/compound_stmts.html#for"><code class="xref std std-keyword docutils literal notranslate"><span class="pre">for</span></code></a> 或 <a class="reference internal" href="../reference/compound_stmts.html#while"><code class="xref std std-keyword docutils literal notranslate"><span class="pre">while</span></code></a> 迴圈:</p>
<div class="highlight-python3 notranslate"><div class="highlight"><pre><span></span><span class="gp">>>> </span><span class="k">for</span> <span class="n">n</span> <span class="ow">in</span> <span class="nb">range</span><span class="p">(</span><span class="mi">2</span><span class="p">,</span> <span class="mi">10</span><span class="p">):</span>
<span class="gp">... </span> <span class="k">for</span> <span class="n">x</span> <span class="ow">in</span> <span class="nb">range</span><span class="p">(</span><span class="mi">2</span><span class="p">,</span> <span class="n">n</span><span class="p">):</span>
<span class="gp">... </span> <span class="k">if</span> <span class="n">n</span> <span class="o">%</span> <span class="n">x</span> <span class="o">==</span> <span class="mi">0</span><span class="p">:</span>
<span class="gp">... </span> <span class="nb">print</span><span class="p">(</span><span class="sa">f</span><span class="s2">"</span><span class="si">{</span><span class="n">n</span><span class="si">}</span><span class="s2"> equals </span><span class="si">{</span><span class="n">x</span><span class="si">}</span><span class="s2"> * </span><span class="si">{</span><span class="n">n</span><span class="o">//</span><span class="n">x</span><span class="si">}</span><span class="s2">"</span><span class="p">)</span>
<span class="gp">... </span> <span class="k">break</span>
<span class="gp">...</span>
<span class="go">4 equals 2 * 2</span>
<span class="go">6 equals 2 * 3</span>
<span class="go">8 equals 2 * 4</span>
<span class="go">9 equals 3 * 3</span>
</pre></div>
</div>
<p><a class="reference internal" href="../reference/simple_stmts.html#continue"><code class="xref std std-keyword docutils literal notranslate"><span class="pre">continue</span></code></a> 陳述式讓所屬的迴圈繼續執行下個疊代:</p>
<div class="highlight-python3 notranslate"><div class="highlight"><pre><span></span><span class="gp">>>> </span><span class="k">for</span> <span class="n">num</span> <span class="ow">in</span> <span class="nb">range</span><span class="p">(</span><span class="mi">2</span><span class="p">,</span> <span class="mi">10</span><span class="p">):</span>
<span class="gp">... </span> <span class="k">if</span> <span class="n">num</span> <span class="o">%</span> <span class="mi">2</span> <span class="o">==</span> <span class="mi">0</span><span class="p">:</span>
<span class="gp">... </span> <span class="nb">print</span><span class="p">(</span><span class="sa">f</span><span class="s2">"Found an even number </span><span class="si">{</span><span class="n">num</span><span class="si">}</span><span class="s2">"</span><span class="p">)</span>
<span class="gp">... </span> <span class="k">continue</span>
<span class="gp">... </span> <span class="nb">print</span><span class="p">(</span><span class="sa">f</span><span class="s2">"Found an odd number </span><span class="si">{</span><span class="n">num</span><span class="si">}</span><span class="s2">"</span><span class="p">)</span>
<span class="gp">...</span>
<span class="go">Found an even number 2</span>
<span class="go">Found an odd number 3</span>
<span class="go">Found an even number 4</span>
<span class="go">Found an odd number 5</span>
<span class="go">Found an even number 6</span>
<span class="go">Found an odd number 7</span>
<span class="go">Found an even number 8</span>
<span class="go">Found an odd number 9</span>
</pre></div>
</div>
</section>
<section id="else-clauses-on-loops">
<span id="break-and-continue-statements-and-else-clauses-on-loops"></span><span id="tut-for-else"></span><h2><span class="section-number">4.5. </span>迴圈的 <code class="xref std std-keyword docutils literal notranslate"><span class="pre">else</span></code> 子句<a class="headerlink" href="#else-clauses-on-loops" title="連結到這個標頭">¶</a></h2>
<p>In a <code class="xref std std-keyword docutils literal notranslate"><span class="pre">for</span></code> or <code class="xref std std-keyword docutils literal notranslate"><span class="pre">while</span></code> loop the <code class="xref std std-keyword docutils literal notranslate"><span class="pre">break</span></code> statement
may be paired with an <code class="xref std std-keyword docutils literal notranslate"><span class="pre">else</span></code> clause. If the loop finishes without
executing the <code class="xref std std-keyword docutils literal notranslate"><span class="pre">break</span></code>, the <code class="xref std std-keyword docutils literal notranslate"><span class="pre">else</span></code> clause executes.</p>
<p>在 <a class="reference internal" href="../reference/compound_stmts.html#for"><code class="xref std std-keyword docutils literal notranslate"><span class="pre">for</span></code></a> 迴圈中,<code class="xref std std-keyword docutils literal notranslate"><span class="pre">else</span></code> 子句會在迴圈完成最終的疊代後執行。</p>
<p>在 <a class="reference internal" href="../reference/compound_stmts.html#while"><code class="xref std std-keyword docutils literal notranslate"><span class="pre">while</span></code></a> 迴圈中,它會在迴圈條件變為 false 後執行。</p>
<p>在任何一種迴圈中,如果迴圈由 <a class="reference internal" href="../reference/simple_stmts.html#break"><code class="xref std std-keyword docutils literal notranslate"><span class="pre">break</span></code></a> 終止,則不會執行 <code class="xref std std-keyword docutils literal notranslate"><span class="pre">else</span></code> 子句。當然其他提早結束迴圈的方式(例如 <a class="reference internal" href="../reference/simple_stmts.html#return"><code class="xref std std-keyword docutils literal notranslate"><span class="pre">return</span></code></a> 或引發例外)也會跳過 <a class="reference internal" href="../reference/compound_stmts.html#else"><code class="xref std std-keyword docutils literal notranslate"><span class="pre">else</span></code></a> 子句的執行。</p>
<p>下面的 <code class="xref std std-keyword docutils literal notranslate"><span class="pre">for</span></code> 迴圈對此進行了舉例說明,該迴圈用以搜索質數:</p>
<div class="highlight-python3 notranslate"><div class="highlight"><pre><span></span><span class="gp">>>> </span><span class="k">for</span> <span class="n">n</span> <span class="ow">in</span> <span class="nb">range</span><span class="p">(</span><span class="mi">2</span><span class="p">,</span> <span class="mi">10</span><span class="p">):</span>
<span class="gp">... </span> <span class="k">for</span> <span class="n">x</span> <span class="ow">in</span> <span class="nb">range</span><span class="p">(</span><span class="mi">2</span><span class="p">,</span> <span class="n">n</span><span class="p">):</span>
<span class="gp">... </span> <span class="k">if</span> <span class="n">n</span> <span class="o">%</span> <span class="n">x</span> <span class="o">==</span> <span class="mi">0</span><span class="p">:</span>
<span class="gp">... </span> <span class="nb">print</span><span class="p">(</span><span class="n">n</span><span class="p">,</span> <span class="s1">'equals'</span><span class="p">,</span> <span class="n">x</span><span class="p">,</span> <span class="s1">'*'</span><span class="p">,</span> <span class="n">n</span><span class="o">//</span><span class="n">x</span><span class="p">)</span>
<span class="gp">... </span> <span class="k">break</span>
<span class="gp">... </span> <span class="k">else</span><span class="p">:</span>
<span class="gp">... </span> <span class="c1"># loop fell through without finding a factor</span>
<span class="gp">... </span> <span class="nb">print</span><span class="p">(</span><span class="n">n</span><span class="p">,</span> <span class="s1">'is a prime number'</span><span class="p">)</span>
<span class="gp">...</span>
<span class="go">2 is a prime number</span>
<span class="go">3 is a prime number</span>
<span class="go">4 equals 2 * 2</span>
<span class="go">5 is a prime number</span>
<span class="go">6 equals 2 * 3</span>
<span class="go">7 is a prime number</span>
<span class="go">8 equals 2 * 4</span>
<span class="go">9 equals 3 * 3</span>
</pre></div>
</div>
<p>(沒錯,這是正確的程式碼。請看仔細:<code class="docutils literal notranslate"><span class="pre">else</span></code> 子句屬於 <code class="docutils literal notranslate"><span class="pre">for</span></code> 迴圈,<strong>並非</strong> <code class="docutils literal notranslate"><span class="pre">if</span></code> 陳述式。)</p>
<p>One way to think of the else clause is to imagine it paired with the <code class="docutils literal notranslate"><span class="pre">if</span></code>
inside the loop. As the loop executes, it will run a sequence like
if/if/if/else. The <code class="docutils literal notranslate"><span class="pre">if</span></code> is inside the loop, encountered a number of times. If
the condition is ever true, a <code class="docutils literal notranslate"><span class="pre">break</span></code> will happen. If the condition is never
true, the <code class="docutils literal notranslate"><span class="pre">else</span></code> clause outside the loop will execute.</p>
<p>當 <code class="docutils literal notranslate"><span class="pre">else</span></code> 子句用於迴圈時,相較於搭配 <code class="docutils literal notranslate"><span class="pre">if</span></code> 陳述式使用,它的行為與 <a class="reference internal" href="../reference/compound_stmts.html#try"><code class="xref std std-keyword docutils literal notranslate"><span class="pre">try</span></code></a> 陳述式中的 <code class="docutils literal notranslate"><span class="pre">else</span></code> 子句更為相似:<code class="docutils literal notranslate"><span class="pre">try</span></code> 陳述式的 <code class="docutils literal notranslate"><span class="pre">else</span></code> 子句在沒有發生例外 (exception) 時執行,而迴圈的 <code class="docutils literal notranslate"><span class="pre">else</span></code> 子句在沒有任何 <code class="docutils literal notranslate"><span class="pre">break</span></code> 發生時執行。更多有關 <code class="docutils literal notranslate"><span class="pre">try</span></code> 陳述式和例外的介紹,見<a class="reference internal" href="errors.html#tut-handling"><span class="std std-ref">處理例外</span></a>。</p>
</section>
<section id="pass-statements">
<span id="tut-pass"></span><h2><span class="section-number">4.6. </span><code class="xref std std-keyword docutils literal notranslate"><span class="pre">pass</span></code> 陳述式<a class="headerlink" href="#pass-statements" title="連結到這個標頭">¶</a></h2>
<p><a class="reference internal" href="../reference/simple_stmts.html#pass"><code class="xref std std-keyword docutils literal notranslate"><span class="pre">pass</span></code></a> 陳述式不執行任何動作。它可用在語法上需要一個陳述式但程式不需要執行任何動作的時候。例如:</p>
<div class="highlight-python3 notranslate"><div class="highlight"><pre><span></span><span class="gp">>>> </span><span class="k">while</span> <span class="kc">True</span><span class="p">:</span>
<span class="gp">... </span> <span class="k">pass</span> <span class="c1"># Busy-wait for keyboard interrupt (Ctrl+C)</span>
<span class="gp">...</span>
</pre></div>
</div>
<p>這經常用於建立簡單的 class(類別):</p>
<div class="highlight-python3 notranslate"><div class="highlight"><pre><span></span><span class="gp">>>> </span><span class="k">class</span><span class="w"> </span><span class="nc">MyEmptyClass</span><span class="p">:</span>
<span class="gp">... </span> <span class="k">pass</span>
<span class="gp">...</span>
</pre></div>
</div>
<p><a class="reference internal" href="../reference/simple_stmts.html#pass"><code class="xref std std-keyword docutils literal notranslate"><span class="pre">pass</span></code></a> 亦可作為一個函式或條件判斷主體的預留位置,在你撰寫新的程式碼時讓你保持在更抽象的思維層次。<code class="xref std std-keyword docutils literal notranslate"><span class="pre">pass</span></code> 會直接被忽略:</p>
<div class="highlight-python3 notranslate"><div class="highlight"><pre><span></span><span class="gp">>>> </span><span class="k">def</span><span class="w"> </span><span class="nf">initlog</span><span class="p">(</span><span class="o">*</span><span class="n">args</span><span class="p">):</span>
<span class="gp">... </span> <span class="k">pass</span> <span class="c1"># Remember to implement this!</span>
<span class="gp">...</span>
</pre></div>
</div>
</section>
<section id="match-statements">
<span id="tut-match"></span><h2><span class="section-number">4.7. </span><code class="xref std std-keyword docutils literal notranslate"><span class="pre">match</span></code> 陳述式<a class="headerlink" href="#match-statements" title="連結到這個標頭">¶</a></h2>
<p><a class="reference internal" href="../reference/compound_stmts.html#match"><code class="xref std std-keyword docutils literal notranslate"><span class="pre">match</span></code></a> 陳述式會拿取一個運算式,並將其值與多個連續的模式 (pattern) 進行比較,這些模式是以一個或多個 case 區塊來表示。表面上,這類似 C、Java 或 JavaScript(以及許多其他語言)中的 switch 陳述式,但它與 Rust 或 Haskell 等語言中的模式匹配 (pattern matching) 更為相近。只有第一個匹配成功的模式會被執行,而它也可以將成分(序列元素或物件屬性)從值中提取到變數中。</p>
<p>最簡單的形式,是將一個主題值 (subject value) 與一個或多個字面值 (literal) 進行比較:</p>
<div class="highlight-python3 notranslate"><div class="highlight"><pre><span></span><span class="k">def</span><span class="w"> </span><span class="nf">http_error</span><span class="p">(</span><span class="n">status</span><span class="p">):</span>
<span class="k">match</span> <span class="n">status</span><span class="p">:</span>
<span class="k">case</span> <span class="mi">400</span><span class="p">:</span>
<span class="k">return</span> <span class="s2">"Bad request"</span>
<span class="k">case</span> <span class="mi">404</span><span class="p">:</span>
<span class="k">return</span> <span class="s2">"Not found"</span>
<span class="k">case</span> <span class="mi">418</span><span class="p">:</span>
<span class="k">return</span> <span class="s2">"I'm a teapot"</span>
<span class="k">case</span><span class="w"> </span><span class="k">_</span><span class="p">:</span>
<span class="k">return</span> <span class="s2">"Something's wrong with the internet"</span>
</pre></div>
</div>
<p>請注意最後一段:「變數名稱」<code class="docutils literal notranslate"><span class="pre">_</span></code> 是作為<em>通用字元 (wildcard)</em>的角色,且永遠不會匹配失敗。如果沒有 case 匹配成功,則不會執行任何的分支。</p>
<p>你可以使用 <code class="docutils literal notranslate"><span class="pre">|</span></code>(「或」)來將多個字面值組合在單一模式中:</p>
<div class="highlight-python3 notranslate"><div class="highlight"><pre><span></span><span class="k">case</span> <span class="mi">401</span> <span class="o">|</span> <span class="mi">403</span> <span class="o">|</span> <span class="mi">404</span><span class="p">:</span>
<span class="k">return</span> <span class="s2">"Not allowed"</span>
</pre></div>
</div>
<p>模式可以看起來像是拆解賦值 (unpacking assignment),且可以用來連結變數:</p>
<div class="highlight-python3 notranslate"><div class="highlight"><pre><span></span><span class="c1"># point is an (x, y) tuple</span>
<span class="k">match</span> <span class="n">point</span><span class="p">:</span>
<span class="k">case</span> <span class="p">(</span><span class="mi">0</span><span class="p">,</span> <span class="mi">0</span><span class="p">):</span>
<span class="nb">print</span><span class="p">(</span><span class="s2">"Origin"</span><span class="p">)</span>
<span class="k">case</span> <span class="p">(</span><span class="mi">0</span><span class="p">,</span> <span class="n">y</span><span class="p">):</span>
<span class="nb">print</span><span class="p">(</span><span class="sa">f</span><span class="s2">"Y=</span><span class="si">{</span><span class="n">y</span><span class="si">}</span><span class="s2">"</span><span class="p">)</span>
<span class="k">case</span> <span class="p">(</span><span class="n">x</span><span class="p">,</span> <span class="mi">0</span><span class="p">):</span>
<span class="nb">print</span><span class="p">(</span><span class="sa">f</span><span class="s2">"X=</span><span class="si">{</span><span class="n">x</span><span class="si">}</span><span class="s2">"</span><span class="p">)</span>
<span class="k">case</span> <span class="p">(</span><span class="n">x</span><span class="p">,</span> <span class="n">y</span><span class="p">):</span>
<span class="nb">print</span><span class="p">(</span><span class="sa">f</span><span class="s2">"X=</span><span class="si">{</span><span class="n">x</span><span class="si">}</span><span class="s2">, Y=</span><span class="si">{</span><span class="n">y</span><span class="si">}</span><span class="s2">"</span><span class="p">)</span>
<span class="k">case</span><span class="w"> </span><span class="k">_</span><span class="p">:</span>
<span class="k">raise</span> <span class="ne">ValueError</span><span class="p">(</span><span class="s2">"Not a point"</span><span class="p">)</span>
</pre></div>
</div>
<p>請仔細研究那個例子!第一個模式有兩個字面值,可以想作是之前所述的字面值模式的延伸。但是接下來的兩個模式結合了一個字面值和一個變數,且該變數<em>繫結 (bind)</em> 了來自主題 (<code class="docutils literal notranslate"><span class="pre">point</span></code>) 的一個值。第四個模式會擷取兩個值,這使得它在概念上類似於拆解賦值 <code class="docutils literal notranslate"><span class="pre">(x,</span> <span class="pre">y)</span> <span class="pre">=</span> <span class="pre">point</span></code>。</p>
<p>如果你要用 class 來結構化你的資料,你可以使用該 class 的名稱加上一個引數列表,類似一個建構式 (constructor),但它能夠將屬性擷取到變數中:</p>
<div class="highlight-python3 notranslate"><div class="highlight"><pre><span></span><span class="k">class</span><span class="w"> </span><span class="nc">Point</span><span class="p">:</span>
<span class="k">def</span><span class="w"> </span><span class="fm">__init__</span><span class="p">(</span><span class="bp">self</span><span class="p">,</span> <span class="n">x</span><span class="p">,</span> <span class="n">y</span><span class="p">):</span>
<span class="bp">self</span><span class="o">.</span><span class="n">x</span> <span class="o">=</span> <span class="n">x</span>
<span class="bp">self</span><span class="o">.</span><span class="n">y</span> <span class="o">=</span> <span class="n">y</span>
<span class="k">def</span><span class="w"> </span><span class="nf">where_is</span><span class="p">(</span><span class="n">point</span><span class="p">):</span>
<span class="k">match</span> <span class="n">point</span><span class="p">:</span>
<span class="k">case</span> <span class="n">Point</span><span class="p">(</span><span class="n">x</span><span class="o">=</span><span class="mi">0</span><span class="p">,</span> <span class="n">y</span><span class="o">=</span><span class="mi">0</span><span class="p">):</span>
<span class="nb">print</span><span class="p">(</span><span class="s2">"Origin"</span><span class="p">)</span>
<span class="k">case</span> <span class="n">Point</span><span class="p">(</span><span class="n">x</span><span class="o">=</span><span class="mi">0</span><span class="p">,</span> <span class="n">y</span><span class="o">=</span><span class="n">y</span><span class="p">):</span>
<span class="nb">print</span><span class="p">(</span><span class="sa">f</span><span class="s2">"Y=</span><span class="si">{</span><span class="n">y</span><span class="si">}</span><span class="s2">"</span><span class="p">)</span>
<span class="k">case</span> <span class="n">Point</span><span class="p">(</span><span class="n">x</span><span class="o">=</span><span class="n">x</span><span class="p">,</span> <span class="n">y</span><span class="o">=</span><span class="mi">0</span><span class="p">):</span>
<span class="nb">print</span><span class="p">(</span><span class="sa">f</span><span class="s2">"X=</span><span class="si">{</span><span class="n">x</span><span class="si">}</span><span class="s2">"</span><span class="p">)</span>
<span class="k">case</span> <span class="n">Point</span><span class="p">():</span>
<span class="nb">print</span><span class="p">(</span><span class="s2">"Somewhere else"</span><span class="p">)</span>
<span class="k">case</span><span class="w"> </span><span class="k">_</span><span class="p">:</span>
<span class="nb">print</span><span class="p">(</span><span class="s2">"Not a point"</span><span class="p">)</span>
</pre></div>
</div>
<p>你可以將位置參數 (positional parameter) 與一些能夠排序其屬性的內建 class(例如 dataclasses)一起使用。你也可以透過在 class 中設定特殊屬性 <code class="docutils literal notranslate"><span class="pre">__match_args__</span></code>,來定義模式中屬性們的特定位置。如果它被設定為 ("x", "y"),則以下的模式都是等價的(且都會將屬性 <code class="docutils literal notranslate"><span class="pre">y</span></code> 連結到變數 <code class="docutils literal notranslate"><span class="pre">var</span></code>):</p>
<div class="highlight-python3 notranslate"><div class="highlight"><pre><span></span><span class="n">Point</span><span class="p">(</span><span class="mi">1</span><span class="p">,</span> <span class="n">var</span><span class="p">)</span>
<span class="n">Point</span><span class="p">(</span><span class="mi">1</span><span class="p">,</span> <span class="n">y</span><span class="o">=</span><span class="n">var</span><span class="p">)</span>
<span class="n">Point</span><span class="p">(</span><span class="n">x</span><span class="o">=</span><span class="mi">1</span><span class="p">,</span> <span class="n">y</span><span class="o">=</span><span class="n">var</span><span class="p">)</span>
<span class="n">Point</span><span class="p">(</span><span class="n">y</span><span class="o">=</span><span class="n">var</span><span class="p">,</span> <span class="n">x</span><span class="o">=</span><span class="mi">1</span><span class="p">)</span>
</pre></div>
</div>
<p>理解模式的一種推薦方法,是將它們看作是你會放在賦值 (assignment) 左側內容的一種延伸形式,這樣就可以了解哪些變數會被設為何值。只有獨立的名稱(像是上面的 <code class="docutils literal notranslate"><span class="pre">var</span></code>)能被 match 陳述式賦值。點分隔名稱(如 <code class="docutils literal notranslate"><span class="pre">foo.bar</span></code>)、屬性名稱(上面的 <code class="docutils literal notranslate"><span class="pre">x=</span></code> 及 <code class="docutils literal notranslate"><span class="pre">y=</span></code>)或 class 名稱(由它們後面的 "(...)" 被辨識,如上面的 <code class="docutils literal notranslate"><span class="pre">Point</span></code>)則永遠無法被賦值。</p>
<p>模式可以任意地被巢套 (nested)。例如,如果我們有一個由某些點所組成的簡短 list,我們就可以像這樣加入 <code class="docutils literal notranslate"><span class="pre">__match_args__</span></code> 來對它進行匹配:</p>
<div class="highlight-python3 notranslate"><div class="highlight"><pre><span></span><span class="k">class</span><span class="w"> </span><span class="nc">Point</span><span class="p">:</span>
<span class="n">__match_args__</span> <span class="o">=</span> <span class="p">(</span><span class="s1">'x'</span><span class="p">,</span> <span class="s1">'y'</span><span class="p">)</span>
<span class="k">def</span><span class="w"> </span><span class="fm">__init__</span><span class="p">(</span><span class="bp">self</span><span class="p">,</span> <span class="n">x</span><span class="p">,</span> <span class="n">y</span><span class="p">):</span>
<span class="bp">self</span><span class="o">.</span><span class="n">x</span> <span class="o">=</span> <span class="n">x</span>
<span class="bp">self</span><span class="o">.</span><span class="n">y</span> <span class="o">=</span> <span class="n">y</span>
<span class="k">match</span> <span class="n">points</span><span class="p">:</span>
<span class="k">case</span> <span class="p">[]:</span>
<span class="nb">print</span><span class="p">(</span><span class="s2">"No points"</span><span class="p">)</span>
<span class="k">case</span> <span class="p">[</span><span class="n">Point</span><span class="p">(</span><span class="mi">0</span><span class="p">,</span> <span class="mi">0</span><span class="p">)]:</span>
<span class="nb">print</span><span class="p">(</span><span class="s2">"The origin"</span><span class="p">)</span>
<span class="k">case</span> <span class="p">[</span><span class="n">Point</span><span class="p">(</span><span class="n">x</span><span class="p">,</span> <span class="n">y</span><span class="p">)]:</span>
<span class="nb">print</span><span class="p">(</span><span class="sa">f</span><span class="s2">"Single point </span><span class="si">{</span><span class="n">x</span><span class="si">}</span><span class="s2">, </span><span class="si">{</span><span class="n">y</span><span class="si">}</span><span class="s2">"</span><span class="p">)</span>
<span class="k">case</span> <span class="p">[</span><span class="n">Point</span><span class="p">(</span><span class="mi">0</span><span class="p">,</span> <span class="n">y1</span><span class="p">),</span> <span class="n">Point</span><span class="p">(</span><span class="mi">0</span><span class="p">,</span> <span class="n">y2</span><span class="p">)]:</span>
<span class="nb">print</span><span class="p">(</span><span class="sa">f</span><span class="s2">"Two on the Y axis at </span><span class="si">{</span><span class="n">y1</span><span class="si">}</span><span class="s2">, </span><span class="si">{</span><span class="n">y2</span><span class="si">}</span><span class="s2">"</span><span class="p">)</span>
<span class="k">case</span><span class="w"> </span><span class="k">_</span><span class="p">:</span>
<span class="nb">print</span><span class="p">(</span><span class="s2">"Something else"</span><span class="p">)</span>
</pre></div>
</div>
<p>我們可以在模式中加入一個 <code class="docutils literal notranslate"><span class="pre">if</span></code> 子句,稱為「防護 (guard)」。如果該防護為假,則 <code class="docutils literal notranslate"><span class="pre">match</span></code> 會繼續嘗試下一個 case 區塊。請注意,值的擷取會發生在防護的評估之前:</p>
<div class="highlight-python3 notranslate"><div class="highlight"><pre><span></span><span class="k">match</span> <span class="n">point</span><span class="p">:</span>
<span class="k">case</span> <span class="n">Point</span><span class="p">(</span><span class="n">x</span><span class="p">,</span> <span class="n">y</span><span class="p">)</span> <span class="k">if</span> <span class="n">x</span> <span class="o">==</span> <span class="n">y</span><span class="p">:</span>
<span class="nb">print</span><span class="p">(</span><span class="sa">f</span><span class="s2">"Y=X at </span><span class="si">{</span><span class="n">x</span><span class="si">}</span><span class="s2">"</span><span class="p">)</span>
<span class="k">case</span> <span class="n">Point</span><span class="p">(</span><span class="n">x</span><span class="p">,</span> <span class="n">y</span><span class="p">):</span>
<span class="nb">print</span><span class="p">(</span><span class="sa">f</span><span class="s2">"Not on the diagonal"</span><span class="p">)</span>
</pre></div>
</div>
<p>此種陳述式的其他幾個重要特色:</p>
<ul>
<li><p>與拆解賦值的情況類似,tuple(元組)和 list 模式具有完全相同的意義,而且實際上可以匹配任意的序列。一個重要的例外,是它們不能匹配疊代器 (iterator) 或字串。</p></li>
<li><p>序列模式 (sequence pattern) 可支援擴充拆解 (extended unpacking):<code class="docutils literal notranslate"><span class="pre">[x,</span> <span class="pre">y,</span> <span class="pre">*rest]</span></code> 與 <code class="docutils literal notranslate"><span class="pre">(x,</span> <span class="pre">y,</span> <span class="pre">*rest)</span></code> 的作用類似於拆解賦值。<code class="docutils literal notranslate"><span class="pre">*</span></code> 後面的名稱也可以是 <code class="docutils literal notranslate"><span class="pre">_</span></code>,所以 <code class="docutils literal notranslate"><span class="pre">(x,</span> <span class="pre">y,</span> <span class="pre">*_)</span></code> 會匹配一個至少兩項的序列,且不會連結那兩項以外的其餘項。</p></li>
<li><p>對映模式 (mapping pattern):<code class="docutils literal notranslate"><span class="pre">{"bandwidth":</span> <span class="pre">b,</span> <span class="pre">"latency":</span> <span class="pre">l}</span></code> 能從一個 dictionary(字典)中擷取 <code class="docutils literal notranslate"><span class="pre">"bandwidth"</span></code> 及 <code class="docutils literal notranslate"><span class="pre">"latency"</span></code> 的值。與序列模式不同,額外的鍵 (key) 會被忽略。一種像是 <code class="docutils literal notranslate"><span class="pre">**rest</span></code> 的拆解方式,也是可被支援的。(但 <code class="docutils literal notranslate"><span class="pre">**_</span></code> 則是多餘的做法,所以它並不被允許。)</p></li>
<li><p>使用關鍵字 <code class="docutils literal notranslate"><span class="pre">as</span></code> 可以擷取子模式 (subpattern):</p>
<div class="highlight-python3 notranslate"><div class="highlight"><pre><span></span><span class="k">case</span> <span class="p">(</span><span class="n">Point</span><span class="p">(</span><span class="n">x1</span><span class="p">,</span> <span class="n">y1</span><span class="p">),</span> <span class="n">Point</span><span class="p">(</span><span class="n">x2</span><span class="p">,</span> <span class="n">y2</span><span class="p">)</span> <span class="k">as</span> <span class="n">p2</span><span class="p">):</span> <span class="o">...</span>
</pre></div>
</div>
<p>將會擷取輸入的第二個元素作為 <code class="docutils literal notranslate"><span class="pre">p2</span></code>(只要該輸入是一個由兩個點所組成的序列)。</p>
</li>
<li><p>大部分的字面值是藉由相等性 (equality) 來比較,但是單例物件 (singleton) <code class="docutils literal notranslate"><span class="pre">True</span></code>、<code class="docutils literal notranslate"><span class="pre">False</span></code> 和 <code class="docutils literal notranslate"><span class="pre">None</span></code> 是藉由標識值 (identity) 來比較。</p></li>
<li><p>模式可以使用附名常數 (named constant)。這些模式必須是點分隔名稱,以免它們被解釋為擷取變數:</p>
<div class="highlight-python3 notranslate"><div class="highlight"><pre><span></span><span class="kn">from</span><span class="w"> </span><span class="nn">enum</span><span class="w"> </span><span class="kn">import</span> <span class="n">Enum</span>
<span class="k">class</span><span class="w"> </span><span class="nc">Color</span><span class="p">(</span><span class="n">Enum</span><span class="p">):</span>
<span class="n">RED</span> <span class="o">=</span> <span class="s1">'red'</span>
<span class="n">GREEN</span> <span class="o">=</span> <span class="s1">'green'</span>
<span class="n">BLUE</span> <span class="o">=</span> <span class="s1">'blue'</span>
<span class="n">color</span> <span class="o">=</span> <span class="n">Color</span><span class="p">(</span><span class="nb">input</span><span class="p">(</span><span class="s2">"Enter your choice of 'red', 'blue' or 'green': "</span><span class="p">))</span>
<span class="k">match</span> <span class="n">color</span><span class="p">:</span>
<span class="k">case</span> <span class="n">Color</span><span class="o">.</span><span class="n">RED</span><span class="p">:</span>
<span class="nb">print</span><span class="p">(</span><span class="s2">"I see red!"</span><span class="p">)</span>
<span class="k">case</span> <span class="n">Color</span><span class="o">.</span><span class="n">GREEN</span><span class="p">:</span>
<span class="nb">print</span><span class="p">(</span><span class="s2">"Grass is green"</span><span class="p">)</span>
<span class="k">case</span> <span class="n">Color</span><span class="o">.</span><span class="n">BLUE</span><span class="p">:</span>
<span class="nb">print</span><span class="p">(</span><span class="s2">"I'm feeling the blues :("</span><span class="p">)</span>
</pre></div>
</div>
</li>
</ul>
<p>關於更詳細的解釋和其他範例,你可以閱讀 <span class="target" id="index-15"></span><a class="pep reference external" href="https://peps.python.org/pep-0636/"><strong>PEP 636</strong></a>,它是以教學的格式編寫而成。</p>
</section>
<section id="defining-functions">
<span id="tut-functions"></span><h2><span class="section-number">4.8. </span>定義函式 (function)<a class="headerlink" href="#defining-functions" title="連結到這個標頭">¶</a></h2>
<p>我們可以建立一個函式來產生費式數列到任何一個上界:</p>
<div class="highlight-python3 notranslate"><div class="highlight"><pre><span></span><span class="gp">>>> </span><span class="k">def</span><span class="w"> </span><span class="nf">fib</span><span class="p">(</span><span class="n">n</span><span class="p">):</span> <span class="c1"># write Fibonacci series less than n</span>
<span class="gp">... </span><span class="w"> </span><span class="sd">"""Print a Fibonacci series less than n."""</span>
<span class="gp">... </span> <span class="n">a</span><span class="p">,</span> <span class="n">b</span> <span class="o">=</span> <span class="mi">0</span><span class="p">,</span> <span class="mi">1</span>
<span class="gp">... </span> <span class="k">while</span> <span class="n">a</span> <span class="o"><</span> <span class="n">n</span><span class="p">:</span>
<span class="gp">... </span> <span class="nb">print</span><span class="p">(</span><span class="n">a</span><span class="p">,</span> <span class="n">end</span><span class="o">=</span><span class="s1">' '</span><span class="p">)</span>
<span class="gp">... </span> <span class="n">a</span><span class="p">,</span> <span class="n">b</span> <span class="o">=</span> <span class="n">b</span><span class="p">,</span> <span class="n">a</span><span class="o">+</span><span class="n">b</span>
<span class="gp">... </span> <span class="nb">print</span><span class="p">()</span>
<span class="gp">...</span>
<span class="gp">>>> </span><span class="c1"># Now call the function we just defined:</span>
<span class="gp">>>> </span><span class="n">fib</span><span class="p">(</span><span class="mi">2000</span><span class="p">)</span>
<span class="go">0 1 1 2 3 5 8 13 21 34 55 89 144 233 377 610 987 1597</span>
</pre></div>
</div>
<p id="index-2">關鍵字 <a class="reference internal" href="../reference/compound_stmts.html#def"><code class="xref std std-keyword docutils literal notranslate"><span class="pre">def</span></code></a> 介紹一個函式的<em>定義</em>。它之後必須連著該函式的名稱和置於括號之中的一串參數。自下一行起,所有縮排的陳述式成為該函式的主體。</p>
<p>一個函式的第一個陳述式可以是一個字串文本;該字串文本被視為該函式的說明文件字串,即 <em class="dfn">docstring</em>。(關於 docstring 的細節請參見<a class="reference internal" href="#tut-docstrings"><span class="std std-ref">說明文件字串 (Documentation Strings)</span></a>段落。)有些工具可以使用 docstring 來自動產生線上或可列印的文件,或讓使用者能以互動的方式在原始碼中瀏覽文件。在原始碼中加入 docstring 是個好慣例,應該養成這樣的習慣。</p>
<p>函式<em>執行</em>時會建立一個新的符號表 (symbol table) 來儲存該函式內的區域變數 (local variable)。更精確地說,所有在函式內的變數賦值都會把該值儲存在一個區域符號表。然而,在引用一個變數時,會先從區域符號表開始搜尋,其次為外層函式的區域符號表,其次為全域符號表 (global symbol table),最後為所有內建的名稱。因此,在函式中,全域變數及外層函式變數雖然可以被引用,但無法被直接賦值(除非全域變數是在 <a class="reference internal" href="../reference/simple_stmts.html#global"><code class="xref std std-keyword docutils literal notranslate"><span class="pre">global</span></code></a> 陳述式中被定義,或外層函式變數在 <a class="reference internal" href="../reference/simple_stmts.html#nonlocal"><code class="xref std std-keyword docutils literal notranslate"><span class="pre">nonlocal</span></code></a> 陳述式中被定義)。</p>
<p>在一個函式被呼叫的時候,實際傳入的參數(引數)會被加入至該函式的區域符號表。因此,引數傳入的方式為<em>傳值呼叫 (call by value)</em>(這裡傳遞的<em>值</em>永遠是一個物件的<em>參照 (reference)</em>,而不是該物件的值)。 <a class="footnote-reference brackets" href="#id2" id="id1" role="doc-noteref"><span class="fn-bracket">[</span>1<span class="fn-bracket">]</span></a> 當一個函式呼叫別的函式或遞迴呼叫它自己時,在被呼叫的函式中會建立一個新的區域符號表。</p>
<p>函式定義時,會把該函式名稱加入至當前的符號表。函式名稱的值帶有一個型別,並被直譯器辨識為使用者自定函式 (user-defined function)。該值可以被指定給別的變數名,使該變數名也可以被當作函式使用。這是常見的重新命名方式:</p>
<div class="highlight-python3 notranslate"><div class="highlight"><pre><span></span><span class="gp">>>> </span><span class="n">fib</span>
<span class="go"><function fib at 10042ed0></span>
<span class="gp">>>> </span><span class="n">f</span> <span class="o">=</span> <span class="n">fib</span>
<span class="gp">>>> </span><span class="n">f</span><span class="p">(</span><span class="mi">100</span><span class="p">)</span>
<span class="go">0 1 1 2 3 5 8 13 21 34 55 89</span>
</pre></div>
</div>
<p>如果你是來自別的語言,你可能不同意 <code class="docutils literal notranslate"><span class="pre">fib</span></code> 是個函式,而是個程序 (procedure),因為它並沒有回傳值。實際上,即使一個函式缺少一個 <a class="reference internal" href="../reference/simple_stmts.html#return"><code class="xref std std-keyword docutils literal notranslate"><span class="pre">return</span></code></a> 陳述式,它亦有一個固定的回傳值。這個值稱為 <code class="docutils literal notranslate"><span class="pre">None</span></code>(它是一個內建名稱)。在直譯器中單獨使用 <code class="docutils literal notranslate"><span class="pre">None</span></code> 時,通常不會被顯示。你可以使用 <a class="reference internal" href="../library/functions.html#print" title="print"><code class="xref py py-func docutils literal notranslate"><span class="pre">print()</span></code></a> 來看到它:</p>
<div class="highlight-python3 notranslate"><div class="highlight"><pre><span></span><span class="gp">>>> </span><span class="n">fib</span><span class="p">(</span><span class="mi">0</span><span class="p">)</span>
<span class="gp">>>> </span><span class="nb">print</span><span class="p">(</span><span class="n">fib</span><span class="p">(</span><span class="mi">0</span><span class="p">))</span>
<span class="go">None</span>
</pre></div>
</div>
<p>如果要寫一個函式回傳費式數列的 list 而不是直接印出它,這也很容易:</p>
<div class="highlight-python3 notranslate"><div class="highlight"><pre><span></span><span class="gp">>>> </span><span class="k">def</span><span class="w"> </span><span class="nf">fib2</span><span class="p">(</span><span class="n">n</span><span class="p">):</span> <span class="c1"># return Fibonacci series up to n</span>
<span class="gp">... </span><span class="w"> </span><span class="sd">"""Return a list containing the Fibonacci series up to n."""</span>
<span class="gp">... </span> <span class="n">result</span> <span class="o">=</span> <span class="p">[]</span>
<span class="gp">... </span> <span class="n">a</span><span class="p">,</span> <span class="n">b</span> <span class="o">=</span> <span class="mi">0</span><span class="p">,</span> <span class="mi">1</span>
<span class="gp">... </span> <span class="k">while</span> <span class="n">a</span> <span class="o"><</span> <span class="n">n</span><span class="p">:</span>
<span class="gp">... </span> <span class="n">result</span><span class="o">.</span><span class="n">append</span><span class="p">(</span><span class="n">a</span><span class="p">)</span> <span class="c1"># see below</span>
<span class="gp">... </span> <span class="n">a</span><span class="p">,</span> <span class="n">b</span> <span class="o">=</span> <span class="n">b</span><span class="p">,</span> <span class="n">a</span><span class="o">+</span><span class="n">b</span>
<span class="gp">... </span> <span class="k">return</span> <span class="n">result</span>
<span class="gp">...</span>
<span class="gp">>>> </span><span class="n">f100</span> <span class="o">=</span> <span class="n">fib2</span><span class="p">(</span><span class="mi">100</span><span class="p">)</span> <span class="c1"># call it</span>
<span class="gp">>>> </span><span class="n">f100</span> <span class="c1"># write the result</span>
<span class="go">[0, 1, 1, 2, 3, 5, 8, 13, 21, 34, 55, 89]</span>
</pre></div>
</div>
<p>這個例子一樣示範了一些新的 Python 特性:</p>
<ul class="simple">
<li><p><a class="reference internal" href="../reference/simple_stmts.html#return"><code class="xref std std-keyword docutils literal notranslate"><span class="pre">return</span></code></a> 陳述式會讓一個函式回傳一個值。單獨使用 <code class="xref std std-keyword docutils literal notranslate"><span class="pre">return</span></code> 不外加一個運算式作為引數時會回傳 <code class="docutils literal notranslate"><span class="pre">None</span></code>。一個函式執行到結束也會回傳 <code class="docutils literal notranslate"><span class="pre">None</span></code>。</p></li>
<li><p><code class="docutils literal notranslate"><span class="pre">result.append(a)</span></code> 陳述式呼叫了一個 list 物件 <code class="docutils literal notranslate"><span class="pre">result</span></code> 的 <em>method(方法)</em>。method 為「屬於」一個物件的函式,命名規則為 <code class="docutils literal notranslate"><span class="pre">obj.methodname</span></code>,其中 <code class="docutils literal notranslate"><span class="pre">obj</span></code> 為某個物件(亦可為一運算式),而 <code class="docutils literal notranslate"><span class="pre">methodname</span></code> 為該 method 的名稱,並由該物件的型別所定義。不同的型別定義不同的 method。不同型別的 method 可以擁有一樣的名稱而不會讓 Python 混淆。(你可以使用 <em>class</em>(類別)定義自己的物件型別和 method,見 <a class="reference internal" href="classes.html#tut-classes"><span class="std std-ref">Class(類別)</span></a>)範例中的 <code class="xref py py-meth docutils literal notranslate"><span class="pre">append()</span></code> method 定義在 list 物件中;它會在該 list 的末端加入一個新的元素。這個例子等同於 <code class="docutils literal notranslate"><span class="pre">result</span> <span class="pre">=</span> <span class="pre">result</span> <span class="pre">+</span> <span class="pre">[a]</span></code>,但更有效率。</p></li>
</ul>
</section>
<section id="more-on-defining-functions">
<span id="tut-defining"></span><h2><span class="section-number">4.9. </span>深入了解函式定義<a class="headerlink" href="#more-on-defining-functions" title="連結到這個標頭">¶</a></h2>
<p>定義函式時使用的引數 (argument) 數量是可變的。總共有三種可以組合使用的形式。</p>
<section id="default-argument-values">
<span id="tut-defaultargs"></span><h3><span class="section-number">4.9.1. </span>預設引數值<a class="headerlink" href="#default-argument-values" title="連結到這個標頭">¶</a></h3>
<p>為一個或多個引數指定預設值是很有用的方式。函式建立後,可以用比定義時更少的引數呼叫該函式。例如:</p>
<div class="highlight-python3 notranslate"><div class="highlight"><pre><span></span><span class="k">def</span><span class="w"> </span><span class="nf">ask_ok</span><span class="p">(</span><span class="n">prompt</span><span class="p">,</span> <span class="n">retries</span><span class="o">=</span><span class="mi">4</span><span class="p">,</span> <span class="n">reminder</span><span class="o">=</span><span class="s1">'Please try again!'</span><span class="p">):</span>
<span class="k">while</span> <span class="kc">True</span><span class="p">:</span>
<span class="n">reply</span> <span class="o">=</span> <span class="nb">input</span><span class="p">(</span><span class="n">prompt</span><span class="p">)</span>
<span class="k">if</span> <span class="n">reply</span> <span class="ow">in</span> <span class="p">{</span><span class="s1">'y'</span><span class="p">,</span> <span class="s1">'ye'</span><span class="p">,</span> <span class="s1">'yes'</span><span class="p">}:</span>
<span class="k">return</span> <span class="kc">True</span>
<span class="k">if</span> <span class="n">reply</span> <span class="ow">in</span> <span class="p">{</span><span class="s1">'n'</span><span class="p">,</span> <span class="s1">'no'</span><span class="p">,</span> <span class="s1">'nop'</span><span class="p">,</span> <span class="s1">'nope'</span><span class="p">}:</span>
<span class="k">return</span> <span class="kc">False</span>
<span class="n">retries</span> <span class="o">=</span> <span class="n">retries</span> <span class="o">-</span> <span class="mi">1</span>
<span class="k">if</span> <span class="n">retries</span> <span class="o"><</span> <span class="mi">0</span><span class="p">:</span>
<span class="k">raise</span> <span class="ne">ValueError</span><span class="p">(</span><span class="s1">'invalid user response'</span><span class="p">)</span>
<span class="nb">print</span><span class="p">(</span><span class="n">reminder</span><span class="p">)</span>
</pre></div>
</div>
<p>該函式可以用以下幾種方式被呼叫:</p>
<ul class="simple">
<li><p>只給必要引數:<code class="docutils literal notranslate"><span class="pre">ask_ok('Do</span> <span class="pre">you</span> <span class="pre">really</span> <span class="pre">want</span> <span class="pre">to</span> <span class="pre">quit?')</span></code></p></li>
<li><p>給予一個選擇性引數:<code class="docutils literal notranslate"><span class="pre">ask_ok('OK</span> <span class="pre">to</span> <span class="pre">overwrite</span> <span class="pre">the</span> <span class="pre">file?',</span> <span class="pre">2)</span></code></p></li>
<li><p>給予所有引數:<code class="docutils literal notranslate"><span class="pre">ask_ok('OK</span> <span class="pre">to</span> <span class="pre">overwrite</span> <span class="pre">the</span> <span class="pre">file?',</span> <span class="pre">2,</span> <span class="pre">'Come</span> <span class="pre">on,</span> <span class="pre">only</span> <span class="pre">yes</span> <span class="pre">or</span> <span class="pre">no!')</span></code></p></li>
</ul>
<p>此例也使用了關鍵字 <a class="reference internal" href="../reference/expressions.html#in"><code class="xref std std-keyword docutils literal notranslate"><span class="pre">in</span></code></a>,用於測試序列中是否包含某個特定值。</p>
<p>預設值是在函式定義當下,於<em>定義時</em>的作用域中求值,所以:</p>
<div class="highlight-python3 notranslate"><div class="highlight"><pre><span></span><span class="n">i</span> <span class="o">=</span> <span class="mi">5</span>
<span class="k">def</span><span class="w"> </span><span class="nf">f</span><span class="p">(</span><span class="n">arg</span><span class="o">=</span><span class="n">i</span><span class="p">):</span>
<span class="nb">print</span><span class="p">(</span><span class="n">arg</span><span class="p">)</span>
<span class="n">i</span> <span class="o">=</span> <span class="mi">6</span>
<span class="n">f</span><span class="p">()</span>
</pre></div>
</div>
<p>將會輸出 <code class="docutils literal notranslate"><span class="pre">5</span></code>。</p>
<p><strong>重要警告</strong>:預設值只求值一次。當預設值為可變物件,例如 list、dictionary(字典)或許多類別實例時,會產生不同的結果。例如,以下函式於後續呼叫時會累積曾經傳遞的引數:</p>
<div class="highlight-python3 notranslate"><div class="highlight"><pre><span></span><span class="k">def</span><span class="w"> </span><span class="nf">f</span><span class="p">(</span><span class="n">a</span><span class="p">,</span> <span class="n">L</span><span class="o">=</span><span class="p">[]):</span>
<span class="n">L</span><span class="o">.</span><span class="n">append</span><span class="p">(</span><span class="n">a</span><span class="p">)</span>
<span class="k">return</span> <span class="n">L</span>
<span class="nb">print</span><span class="p">(</span><span class="n">f</span><span class="p">(</span><span class="mi">1</span><span class="p">))</span>
<span class="nb">print</span><span class="p">(</span><span class="n">f</span><span class="p">(</span><span class="mi">2</span><span class="p">))</span>
<span class="nb">print</span><span class="p">(</span><span class="n">f</span><span class="p">(</span><span class="mi">3</span><span class="p">))</span>
</pre></div>
</div>
<p>將會輸出:</p>
<div class="highlight-python3 notranslate"><div class="highlight"><pre><span></span><span class="p">[</span><span class="mi">1</span><span class="p">]</span>
<span class="p">[</span><span class="mi">1</span><span class="p">,</span> <span class="mi">2</span><span class="p">]</span>
<span class="p">[</span><span class="mi">1</span><span class="p">,</span> <span class="mi">2</span><span class="p">,</span> <span class="mi">3</span><span class="p">]</span>
</pre></div>
</div>
<p>如果不想在後續呼叫之間共用預設值,應以如下方式編寫函式:</p>
<div class="highlight-python3 notranslate"><div class="highlight"><pre><span></span><span class="k">def</span><span class="w"> </span><span class="nf">f</span><span class="p">(</span><span class="n">a</span><span class="p">,</span> <span class="n">L</span><span class="o">=</span><span class="kc">None</span><span class="p">):</span>
<span class="k">if</span> <span class="n">L</span> <span class="ow">is</span> <span class="kc">None</span><span class="p">:</span>
<span class="n">L</span> <span class="o">=</span> <span class="p">[]</span>
<span class="n">L</span><span class="o">.</span><span class="n">append</span><span class="p">(</span><span class="n">a</span><span class="p">)</span>
<span class="k">return</span> <span class="n">L</span>
</pre></div>
</div>
</section>
<section id="keyword-arguments">
<span id="tut-keywordargs"></span><h3><span class="section-number">4.9.2. </span>關鍵字引數<a class="headerlink" href="#keyword-arguments" title="連結到這個標頭">¶</a></h3>
<p>函式也可以使用<a class="reference internal" href="../glossary.html#term-keyword-argument"><span class="xref std std-term">關鍵字引數</span></a>,以 <code class="docutils literal notranslate"><span class="pre">kwarg=value</span></code> 的形式呼叫。舉例來說,以下函式:</p>
<div class="highlight-python3 notranslate"><div class="highlight"><pre><span></span><span class="k">def</span><span class="w"> </span><span class="nf">parrot</span><span class="p">(</span><span class="n">voltage</span><span class="p">,</span> <span class="n">state</span><span class="o">=</span><span class="s1">'a stiff'</span><span class="p">,</span> <span class="n">action</span><span class="o">=</span><span class="s1">'voom'</span><span class="p">,</span> <span class="nb">type</span><span class="o">=</span><span class="s1">'Norwegian Blue'</span><span class="p">):</span>
<span class="nb">print</span><span class="p">(</span><span class="s2">"-- This parrot wouldn't"</span><span class="p">,</span> <span class="n">action</span><span class="p">,</span> <span class="n">end</span><span class="o">=</span><span class="s1">' '</span><span class="p">)</span>
<span class="nb">print</span><span class="p">(</span><span class="s2">"if you put"</span><span class="p">,</span> <span class="n">voltage</span><span class="p">,</span> <span class="s2">"volts through it."</span><span class="p">)</span>
<span class="nb">print</span><span class="p">(</span><span class="s2">"-- Lovely plumage, the"</span><span class="p">,</span> <span class="nb">type</span><span class="p">)</span>
<span class="nb">print</span><span class="p">(</span><span class="s2">"-- It's"</span><span class="p">,</span> <span class="n">state</span><span class="p">,</span> <span class="s2">"!"</span><span class="p">)</span>
</pre></div>
</div>
<p>接受一個必要引數 (<code class="docutils literal notranslate"><span class="pre">voltage</span></code>) 和三個選擇性引數 (<code class="docutils literal notranslate"><span class="pre">state</span></code>,<code class="docutils literal notranslate"><span class="pre">action</span></code>,和 <code class="docutils literal notranslate"><span class="pre">type</span></code>)。該函式可用下列任一方式呼叫:</p>
<div class="highlight-python3 notranslate"><div class="highlight"><pre><span></span><span class="n">parrot</span><span class="p">(</span><span class="mi">1000</span><span class="p">)</span> <span class="c1"># 1 positional argument</span>
<span class="n">parrot</span><span class="p">(</span><span class="n">voltage</span><span class="o">=</span><span class="mi">1000</span><span class="p">)</span> <span class="c1"># 1 keyword argument</span>
<span class="n">parrot</span><span class="p">(</span><span class="n">voltage</span><span class="o">=</span><span class="mi">1000000</span><span class="p">,</span> <span class="n">action</span><span class="o">=</span><span class="s1">'VOOOOOM'</span><span class="p">)</span> <span class="c1"># 2 keyword arguments</span>
<span class="n">parrot</span><span class="p">(</span><span class="n">action</span><span class="o">=</span><span class="s1">'VOOOOOM'</span><span class="p">,</span> <span class="n">voltage</span><span class="o">=</span><span class="mi">1000000</span><span class="p">)</span> <span class="c1"># 2 keyword arguments</span>
<span class="n">parrot</span><span class="p">(</span><span class="s1">'a million'</span><span class="p">,</span> <span class="s1">'bereft of life'</span><span class="p">,</span> <span class="s1">'jump'</span><span class="p">)</span> <span class="c1"># 3 positional arguments</span>
<span class="n">parrot</span><span class="p">(</span><span class="s1">'a thousand'</span><span class="p">,</span> <span class="n">state</span><span class="o">=</span><span class="s1">'pushing up the daisies'</span><span class="p">)</span> <span class="c1"># 1 positional, 1 keyword</span>
</pre></div>
</div>
<p>但以下呼叫方式都無效:</p>
<div class="highlight-python3 notranslate"><div class="highlight"><pre><span></span><span class="n">parrot</span><span class="p">()</span> <span class="c1"># required argument missing</span>
<span class="n">parrot</span><span class="p">(</span><span class="n">voltage</span><span class="o">=</span><span class="mf">5.0</span><span class="p">,</span> <span class="s1">'dead'</span><span class="p">)</span> <span class="c1"># non-keyword argument after a keyword argument</span>
<span class="n">parrot</span><span class="p">(</span><span class="mi">110</span><span class="p">,</span> <span class="n">voltage</span><span class="o">=</span><span class="mi">220</span><span class="p">)</span> <span class="c1"># duplicate value for the same argument</span>
<span class="n">parrot</span><span class="p">(</span><span class="n">actor</span><span class="o">=</span><span class="s1">'John Cleese'</span><span class="p">)</span> <span class="c1"># unknown keyword argument</span>
</pre></div>
</div>
<p>函式呼叫時,關鍵字引數 (keyword argument) 必須在位置引數 (positional argument) 後面。所有傳遞的關鍵字引數都必須匹配一個可被函式接受的引數(<code class="docutils literal notranslate"><span class="pre">actor</span></code> 不是 <code class="docutils literal notranslate"><span class="pre">parrot</span></code> 函式的有效引數),而關鍵字引數的順序並不重要。此規則也包括必要引數,(<code class="docutils literal notranslate"><span class="pre">parrot(voltage=1000)</span></code> 也有效)。一個引數不可多次被賦值,下面就是一個因此限制而無效的例子:</p>
<div class="highlight-python3 notranslate"><div class="highlight"><pre><span></span><span class="gp">>>> </span><span class="k">def</span><span class="w"> </span><span class="nf">function</span><span class="p">(</span><span class="n">a</span><span class="p">):</span>
<span class="gp">... </span> <span class="k">pass</span>
<span class="gp">...</span>
<span class="gp">>>> </span><span class="n">function</span><span class="p">(</span><span class="mi">0</span><span class="p">,</span> <span class="n">a</span><span class="o">=</span><span class="mi">0</span><span class="p">)</span>
<span class="gt">Traceback (most recent call last):</span>
File <span class="nb">"<stdin>"</span>, line <span class="m">1</span>, in <span class="n"><module></span>
<span class="gr">TypeError</span>: <span class="n">function() got multiple values for argument 'a'</span>
</pre></div>
</div>
<p>當最後一個參數為 <code class="docutils literal notranslate"><span class="pre">**name</span></code> 形式時,它接收一個 dictionary(字典,詳見 <a class="reference internal" href="../library/stdtypes.html#typesmapping"><span class="std std-ref">Mapping Types --- dict</span></a>),該字典包含所有可對應形式參數以外的關鍵字引數。<code class="docutils literal notranslate"><span class="pre">**name</span></code> 可以與 <code class="docutils literal notranslate"><span class="pre">*name</span></code> 參數(下一小節介紹)組合使用,<code class="docutils literal notranslate"><span class="pre">*name</span></code> 接收一個 <a class="reference internal" href="datastructures.html#tut-tuples"><span class="std std-ref">tuple</span></a>,該 tuple 包含一般參數以外的位置引數(<code class="docutils literal notranslate"><span class="pre">*name</span></code> 必須出現在 <code class="docutils literal notranslate"><span class="pre">**name</span></code> 前面)。例如,若我們定義這樣的函式:</p>
<div class="highlight-python3 notranslate"><div class="highlight"><pre><span></span><span class="k">def</span><span class="w"> </span><span class="nf">cheeseshop</span><span class="p">(</span><span class="n">kind</span><span class="p">,</span> <span class="o">*</span><span class="n">arguments</span><span class="p">,</span> <span class="o">**</span><span class="n">keywords</span><span class="p">):</span>
<span class="nb">print</span><span class="p">(</span><span class="s2">"-- Do you have any"</span><span class="p">,</span> <span class="n">kind</span><span class="p">,</span> <span class="s2">"?"</span><span class="p">)</span>
<span class="nb">print</span><span class="p">(</span><span class="s2">"-- I'm sorry, we're all out of"</span><span class="p">,</span> <span class="n">kind</span><span class="p">)</span>
<span class="k">for</span> <span class="n">arg</span> <span class="ow">in</span> <span class="n">arguments</span><span class="p">:</span>
<span class="nb">print</span><span class="p">(</span><span class="n">arg</span><span class="p">)</span>
<span class="nb">print</span><span class="p">(</span><span class="s2">"-"</span> <span class="o">*</span> <span class="mi">40</span><span class="p">)</span>
<span class="k">for</span> <span class="n">kw</span> <span class="ow">in</span> <span class="n">keywords</span><span class="p">:</span>
<span class="nb">print</span><span class="p">(</span><span class="n">kw</span><span class="p">,</span> <span class="s2">":"</span><span class="p">,</span> <span class="n">keywords</span><span class="p">[</span><span class="n">kw</span><span class="p">])</span>
</pre></div>
</div>
<p>它可以被如此呼叫:</p>
<div class="highlight-python3 notranslate"><div class="highlight"><pre><span></span><span class="n">cheeseshop</span><span class="p">(</span><span class="s2">"Limburger"</span><span class="p">,</span> <span class="s2">"It's very runny, sir."</span><span class="p">,</span>
<span class="s2">"It's really very, VERY runny, sir."</span><span class="p">,</span>
<span class="n">shopkeeper</span><span class="o">=</span><span class="s2">"Michael Palin"</span><span class="p">,</span>
<span class="n">client</span><span class="o">=</span><span class="s2">"John Cleese"</span><span class="p">,</span>
<span class="n">sketch</span><span class="o">=</span><span class="s2">"Cheese Shop Sketch"</span><span class="p">)</span>
</pre></div>
</div>
<p>輸出結果如下:</p>
<div class="highlight-none notranslate"><div class="highlight"><pre><span></span>-- Do you have any Limburger ?
-- I'm sorry, we're all out of Limburger
It's very runny, sir.
It's really very, VERY runny, sir.
----------------------------------------
shopkeeper : Michael Palin
client : John Cleese
sketch : Cheese Shop Sketch
</pre></div>
</div>
<p>注意,關鍵字引數的輸出順序與呼叫函式時被提供的順序必定一致。</p>
</section>
<section id="special-parameters">
<h3><span class="section-number">4.9.3. </span>特殊參數<a class="headerlink" href="#special-parameters" title="連結到這個標頭">¶</a></h3>
<p>在預設情況,引數能以位置或明確地以關鍵字傳遞给 Python 函式。為了程式的可讀性及效能,限制引數的傳遞方式是合理的,如此,開發者只需查看函式定義,即可確定各項目是按位置,按位置或關鍵字,還是按關鍵字傳遞。</p>
<p>函式定義可能如以下樣式:</p>
<div class="highlight-none notranslate"><div class="highlight"><pre><span></span>def f(pos1, pos2, /, pos_or_kwd, *, kwd1, kwd2):
----------- ---------- ----------
| | |
| Positional or keyword |
| - Keyword only
-- Positional only
</pre></div>
</div>
<p><code class="docutils literal notranslate"><span class="pre">/</span></code> 和 <code class="docutils literal notranslate"><span class="pre">*</span></code> 是選擇性的。這些符號若被使用,是表明引數被傳遞給函式的參數種類:僅限位置、位置或關鍵字、僅限關鍵字。關鍵字參數也稱為附名參數 (named parameters)。</p>
<section id="positional-or-keyword-arguments">
<h4><span class="section-number">4.9.3.1. </span>位置或關鍵字引數 (Positional-or-Keyword Arguments)<a class="headerlink" href="#positional-or-keyword-arguments" title="連結到這個標頭">¶</a></h4>
<p>若函式定義中未使用 <code class="docutils literal notranslate"><span class="pre">/</span></code> 和 <code class="docutils literal notranslate"><span class="pre">*</span></code> 時,引數可以按位置或關鍵字傳遞給函式。</p>
</section>
<section id="positional-only-parameters">
<h4><span class="section-number">4.9.3.2. </span>僅限位置參數 (Positional-Only Parameters)<a class="headerlink" href="#positional-only-parameters" title="連結到這個標頭">¶</a></h4>
<p>此處再詳述一些細節,特定參數可以標記為<em>僅限位置</em>。若參數為<em>僅限位置</em>時,它們的順序很重要,且這些參數不能用關鍵字傳遞。僅限位置參數必須放在 <code class="docutils literal notranslate"><span class="pre">/</span></code>(斜線)之前。<code class="docutils literal notranslate"><span class="pre">/</span></code> 用於在邏輯上分開僅限位置參數與其餘參數。如果函式定義中沒有 <code class="docutils literal notranslate"><span class="pre">/</span></code>,則表示沒有任何僅限位置參數。</p>
<p><code class="docutils literal notranslate"><span class="pre">/</span></code> 後面的參數可以是<em>位置或關鍵字</em>或<em>僅限關鍵字</em>參數。</p>
</section>
<section id="keyword-only-arguments">
<h4><span class="section-number">4.9.3.3. </span>僅限關鍵字引數 (Keyword-Only Arguments)<a class="headerlink" href="#keyword-only-arguments" title="連結到這個標頭">¶</a></h4>
<p>要把參數標記為<em>僅限關鍵字</em>,表明參數必須以關鍵字引數傳遞,必須在引數列表中第一個<em>僅限關鍵字</em>參數前放上 <code class="docutils literal notranslate"><span class="pre">*</span></code>。</p>
</section>
<section id="function-examples">
<h4><span class="section-number">4.9.3.4. </span>函式範例<a class="headerlink" href="#function-examples" title="連結到這個標頭">¶</a></h4>
<p>請看以下的函式定義範例,注意 <code class="docutils literal notranslate"><span class="pre">/</span></code> 和 <code class="docutils literal notranslate"><span class="pre">*</span></code> 記號:</p>
<div class="highlight-python3 notranslate"><div class="highlight"><pre><span></span><span class="gp">>>> </span><span class="k">def</span><span class="w"> </span><span class="nf">standard_arg</span><span class="p">(</span><span class="n">arg</span><span class="p">):</span>
<span class="gp">... </span> <span class="nb">print</span><span class="p">(</span><span class="n">arg</span><span class="p">)</span>
<span class="gp">...</span>
<span class="gp">>>> </span><span class="k">def</span><span class="w"> </span><span class="nf">pos_only_arg</span><span class="p">(</span><span class="n">arg</span><span class="p">,</span> <span class="o">/</span><span class="p">):</span>
<span class="gp">... </span> <span class="nb">print</span><span class="p">(</span><span class="n">arg</span><span class="p">)</span>
<span class="gp">...</span>
<span class="gp">>>> </span><span class="k">def</span><span class="w"> </span><span class="nf">kwd_only_arg</span><span class="p">(</span><span class="o">*</span><span class="p">,</span> <span class="n">arg</span><span class="p">):</span>
<span class="gp">... </span> <span class="nb">print</span><span class="p">(</span><span class="n">arg</span><span class="p">)</span>
<span class="gp">...</span>
<span class="gp">>>> </span><span class="k">def</span><span class="w"> </span><span class="nf">combined_example</span><span class="p">(</span><span class="n">pos_only</span><span class="p">,</span> <span class="o">/</span><span class="p">,</span> <span class="n">standard</span><span class="p">,</span> <span class="o">*</span><span class="p">,</span> <span class="n">kwd_only</span><span class="p">):</span>
<span class="gp">... </span> <span class="nb">print</span><span class="p">(</span><span class="n">pos_only</span><span class="p">,</span> <span class="n">standard</span><span class="p">,</span> <span class="n">kwd_only</span><span class="p">)</span>
</pre></div>
</div>
<p>第一個函式定義 <code class="docutils literal notranslate"><span class="pre">standard_arg</span></code> 是我們最熟悉的形式,對呼叫方式沒有任何限制,可以按位置或關鍵字傳遞引數:</p>
<div class="highlight-python3 notranslate"><div class="highlight"><pre><span></span><span class="gp">>>> </span><span class="n">standard_arg</span><span class="p">(</span><span class="mi">2</span><span class="p">)</span>
<span class="go">2</span>
<span class="gp">>>> </span><span class="n">standard_arg</span><span class="p">(</span><span class="n">arg</span><span class="o">=</span><span class="mi">2</span><span class="p">)</span>
<span class="go">2</span>
</pre></div>
</div>
<p>第二個函式 <code class="docutils literal notranslate"><span class="pre">pos_only_arg</span></code> 的函式定義中有 <code class="docutils literal notranslate"><span class="pre">/</span></code>,因此僅限使用位置參數:</p>
<div class="highlight-python3 notranslate"><div class="highlight"><pre><span></span><span class="gp">>>> </span><span class="n">pos_only_arg</span><span class="p">(</span><span class="mi">1</span><span class="p">)</span>
<span class="go">1</span>
<span class="gp">>>> </span><span class="n">pos_only_arg</span><span class="p">(</span><span class="n">arg</span><span class="o">=</span><span class="mi">1</span><span class="p">)</span>
<span class="gt">Traceback (most recent call last):</span>
File <span class="nb">"<stdin>"</span>, line <span class="m">1</span>, in <span class="n"><module></span>
<span class="gr">TypeError</span>: <span class="n">pos_only_arg() got some positional-only arguments passed as keyword arguments: 'arg'</span>
</pre></div>
</div>
<p>第三個函式 <code class="docutils literal notranslate"><span class="pre">kwd_only_arg</span></code> 的函式定義透過 <code class="docutils literal notranslate"><span class="pre">*</span></code> 表明僅限關鍵字引數:</p>
<div class="highlight-python3 notranslate"><div class="highlight"><pre><span></span><span class="gp">>>> </span><span class="n">kwd_only_arg</span><span class="p">(</span><span class="mi">3</span><span class="p">)</span>
<span class="gt">Traceback (most recent call last):</span>
File <span class="nb">"<stdin>"</span>, line <span class="m">1</span>, in <span class="n"><module></span>
<span class="gr">TypeError</span>: <span class="n">kwd_only_arg() takes 0 positional arguments but 1 was given</span>
<span class="gp">>>> </span><span class="n">kwd_only_arg</span><span class="p">(</span><span class="n">arg</span><span class="o">=</span><span class="mi">3</span><span class="p">)</span>
<span class="go">3</span>
</pre></div>
</div>
<p>最後一個函式在同一個函式定義中,使用了全部三種呼叫方式:</p>
<div class="highlight-python3 notranslate"><div class="highlight"><pre><span></span><span class="gp">>>> </span><span class="n">combined_example</span><span class="p">(</span><span class="mi">1</span><span class="p">,</span> <span class="mi">2</span><span class="p">,</span> <span class="mi">3</span><span class="p">)</span>
<span class="gt">Traceback (most recent call last):</span>
File <span class="nb">"<stdin>"</span>, line <span class="m">1</span>, in <span class="n"><module></span>
<span class="gr">TypeError</span>: <span class="n">combined_example() takes 2 positional arguments but 3 were given</span>
<span class="gp">>>> </span><span class="n">combined_example</span><span class="p">(</span><span class="mi">1</span><span class="p">,</span> <span class="mi">2</span><span class="p">,</span> <span class="n">kwd_only</span><span class="o">=</span><span class="mi">3</span><span class="p">)</span>
<span class="go">1 2 3</span>
<span class="gp">>>> </span><span class="n">combined_example</span><span class="p">(</span><span class="mi">1</span><span class="p">,</span> <span class="n">standard</span><span class="o">=</span><span class="mi">2</span><span class="p">,</span> <span class="n">kwd_only</span><span class="o">=</span><span class="mi">3</span><span class="p">)</span>
<span class="go">1 2 3</span>
<span class="gp">>>> </span><span class="n">combined_example</span><span class="p">(</span><span class="n">pos_only</span><span class="o">=</span><span class="mi">1</span><span class="p">,</span> <span class="n">standard</span><span class="o">=</span><span class="mi">2</span><span class="p">,</span> <span class="n">kwd_only</span><span class="o">=</span><span class="mi">3</span><span class="p">)</span>
<span class="gt">Traceback (most recent call last):</span>
File <span class="nb">"<stdin>"</span>, line <span class="m">1</span>, in <span class="n"><module></span>
<span class="gr">TypeError</span>: <span class="n">combined_example() got some positional-only arguments passed as keyword arguments: 'pos_only'</span>
</pre></div>
</div>
<p>最後,請看這個函式定義,如果 <code class="docutils literal notranslate"><span class="pre">**kwds</span></code> 內有 <code class="docutils literal notranslate"><span class="pre">name</span></code> 這個鍵,可能與位置引數 <code class="docutils literal notranslate"><span class="pre">name</span></code> 產生潛在衝突:</p>
<div class="highlight-python3 notranslate"><div class="highlight"><pre><span></span><span class="k">def</span><span class="w"> </span><span class="nf">foo</span><span class="p">(</span><span class="n">name</span><span class="p">,</span> <span class="o">**</span><span class="n">kwds</span><span class="p">):</span>
<span class="k">return</span> <span class="s1">'name'</span> <span class="ow">in</span> <span class="n">kwds</span>
</pre></div>
</div>
<p>呼叫該函式不可能回傳 <code class="docutils literal notranslate"><span class="pre">True</span></code>,因為關鍵字 <code class="docutils literal notranslate"><span class="pre">'name'</span></code> 永遠是連結在第一個參數。例如:</p>
<div class="highlight-python3 notranslate"><div class="highlight"><pre><span></span><span class="gp">>>> </span><span class="n">foo</span><span class="p">(</span><span class="mi">1</span><span class="p">,</span> <span class="o">**</span><span class="p">{</span><span class="s1">'name'</span><span class="p">:</span> <span class="mi">2</span><span class="p">})</span>
<span class="gt">Traceback (most recent call last):</span>
File <span class="nb">"<stdin>"</span>, line <span class="m">1</span>, in <span class="n"><module></span>
<span class="gr">TypeError</span>: <span class="n">foo() got multiple values for argument 'name'</span>
<span class="gp">>>></span>
</pre></div>
</div>
<p>使用 <code class="docutils literal notranslate"><span class="pre">/</span></code>(僅限位置引數)後,就可以了。函式定義會允許 <code class="docutils literal notranslate"><span class="pre">name</span></code> 當作位置引數,而 <code class="docutils literal notranslate"><span class="pre">'name'</span></code> 也可以當作關鍵字引數中的鍵:</p>
<div class="highlight-python3 notranslate"><div class="highlight"><pre><span></span><span class="gp">>>> </span><span class="k">def</span><span class="w"> </span><span class="nf">foo</span><span class="p">(</span><span class="n">name</span><span class="p">,</span> <span class="o">/</span><span class="p">,</span> <span class="o">**</span><span class="n">kwds</span><span class="p">):</span>
<span class="gp">... </span> <span class="k">return</span> <span class="s1">'name'</span> <span class="ow">in</span> <span class="n">kwds</span>
<span class="gp">...</span>
<span class="gp">>>> </span><span class="n">foo</span><span class="p">(</span><span class="mi">1</span><span class="p">,</span> <span class="o">**</span><span class="p">{</span><span class="s1">'name'</span><span class="p">:</span> <span class="mi">2</span><span class="p">})</span>
<span class="go">True</span>
</pre></div>
</div>
<p>換句話說,僅限位置參數的名稱可以在 <code class="docutils literal notranslate"><span class="pre">**kwds</span></code> 中使用,而不產生歧義。</p>
</section>
<section id="recap">
<h4><span class="section-number">4.9.3.5. </span>回顧<a class="headerlink" href="#recap" title="連結到這個標頭">¶</a></h4>
<p>此用例決定哪些參數可以用於函式定義:</p>
<div class="highlight-python3 notranslate"><div class="highlight"><pre><span></span><span class="k">def</span><span class="w"> </span><span class="nf">f</span><span class="p">(</span><span class="n">pos1</span><span class="p">,</span> <span class="n">pos2</span><span class="p">,</span> <span class="o">/</span><span class="p">,</span> <span class="n">pos_or_kwd</span><span class="p">,</span> <span class="o">*</span><span class="p">,</span> <span class="n">kwd1</span><span class="p">,</span> <span class="n">kwd2</span><span class="p">):</span>
</pre></div>
</div>
<p>說明:</p>
<ul class="simple">
<li><p>如果不想讓使用者使用參數名稱,請使用僅限位置。當參數名稱沒有實際意義時,若你想控制引數在函式呼叫的排列順序,或同時使用位置參數和任意關鍵字時,這種方式很有用。</p></li>
<li><p>當參數名稱有意義,且明確的名稱可讓函式定義更易理解,或是你不希望使用者依賴引數被傳遞時的位置時,請使用僅限關鍵字。</p></li>
<li><p>對於應用程式介面 (API),使用僅限位置,以防止未來參數名稱被修改時造成 API 的中斷性變更。</p></li>
</ul>
</section>
</section>
<section id="arbitrary-argument-lists">
<span id="tut-arbitraryargs"></span><h3><span class="section-number">4.9.4. </span>任意引數列表 (Arbitrary Argument Lists)<a class="headerlink" href="#arbitrary-argument-lists" title="連結到這個標頭">¶</a></h3>
<p id="index-3">最後,有個較不常用的選項,是規定函式被呼叫時,可以使用任意數量的引數。這些引數會被包裝進一個 tuple 中(詳見 <a class="reference internal" href="datastructures.html#tut-tuples"><span class="std std-ref">Tuples 和序列 (Sequences)</span></a>)。在可變數量的引數之前,可能有零個或多個普通引數:</p>
<div class="highlight-python3 notranslate"><div class="highlight"><pre><span></span><span class="k">def</span><span class="w"> </span><span class="nf">write_multiple_items</span><span class="p">(</span><span class="n">file</span><span class="p">,</span> <span class="n">separator</span><span class="p">,</span> <span class="o">*</span><span class="n">args</span><span class="p">):</span>
<span class="n">file</span><span class="o">.</span><span class="n">write</span><span class="p">(</span><span class="n">separator</span><span class="o">.</span><span class="n">join</span><span class="p">(</span><span class="n">args</span><span class="p">))</span>
</pre></div>
</div>
<p>通常,這些 <em>variadic</em>(可變的)引數會出現在參數列表的最末端,這樣它們就可以把所有傳遞給函式的剩餘輸入引數都撈起來。出現在 <code class="docutils literal notranslate"><span class="pre">*args</span></code> 參數後面的任何參數必須是「僅限關鍵字」引數,意即它們只能作為關鍵字引數,而不能用作位置引數。</p>
<div class="highlight-python3 notranslate"><div class="highlight"><pre><span></span><span class="gp">>>> </span><span class="k">def</span><span class="w"> </span><span class="nf">concat</span><span class="p">(</span><span class="o">*</span><span class="n">args</span><span class="p">,</span> <span class="n">sep</span><span class="o">=</span><span class="s2">"/"</span><span class="p">):</span>
<span class="gp">... </span> <span class="k">return</span> <span class="n">sep</span><span class="o">.</span><span class="n">join</span><span class="p">(</span><span class="n">args</span><span class="p">)</span>
<span class="gp">...</span>
<span class="gp">>>> </span><span class="n">concat</span><span class="p">(</span><span class="s2">"earth"</span><span class="p">,</span> <span class="s2">"mars"</span><span class="p">,</span> <span class="s2">"venus"</span><span class="p">)</span>
<span class="go">'earth/mars/venus'</span>
<span class="gp">>>> </span><span class="n">concat</span><span class="p">(</span><span class="s2">"earth"</span><span class="p">,</span> <span class="s2">"mars"</span><span class="p">,</span> <span class="s2">"venus"</span><span class="p">,</span> <span class="n">sep</span><span class="o">=</span><span class="s2">"."</span><span class="p">)</span>
<span class="go">'earth.mars.venus'</span>
</pre></div>
</div>
</section>
<section id="unpacking-argument-lists">
<span id="tut-unpacking-arguments"></span><h3><span class="section-number">4.9.5. </span>拆解引數列表(Unpacking Argument Lists)<a class="headerlink" href="#unpacking-argument-lists" title="連結到這個標頭">¶</a></h3>
<p>當引數們已經存在一個 list 或 tuple 裡,但為了滿足一個需要個別位置引數的函式呼叫,而去拆解它們時,情況就剛好相反。例如,內建的 <a class="reference internal" href="../library/stdtypes.html#range" title="range"><code class="xref py py-func docutils literal notranslate"><span class="pre">range()</span></code></a> 函式要求分開的 <em>start</em> 和 <em>stop</em> 引數。如果這些引數不是分開的,則要在呼叫函式時,用 <code class="docutils literal notranslate"><span class="pre">*</span></code> 運算子把引數們從 list 或 tuple 中拆解出來:</p>
<div class="highlight-python3 notranslate"><div class="highlight"><pre><span></span><span class="gp">>>> </span><span class="nb">list</span><span class="p">(</span><span class="nb">range</span><span class="p">(</span><span class="mi">3</span><span class="p">,</span> <span class="mi">6</span><span class="p">))</span> <span class="c1"># normal call with separate arguments</span>
<span class="go">[3, 4, 5]</span>
<span class="gp">>>> </span><span class="n">args</span> <span class="o">=</span> <span class="p">[</span><span class="mi">3</span><span class="p">,</span> <span class="mi">6</span><span class="p">]</span>
<span class="gp">>>> </span><span class="nb">list</span><span class="p">(</span><span class="nb">range</span><span class="p">(</span><span class="o">*</span><span class="n">args</span><span class="p">))</span> <span class="c1"># call with arguments unpacked from a list</span>
<span class="go">[3, 4, 5]</span>
</pre></div>
</div>
<p id="index-4">同樣地,dictionary(字典)可以用 <code class="docutils literal notranslate"><span class="pre">**</span></code> 運算子傳遞關鍵字引數:</p>
<div class="highlight-python3 notranslate"><div class="highlight"><pre><span></span><span class="gp">>>> </span><span class="k">def</span><span class="w"> </span><span class="nf">parrot</span><span class="p">(</span><span class="n">voltage</span><span class="p">,</span> <span class="n">state</span><span class="o">=</span><span class="s1">'a stiff'</span><span class="p">,</span> <span class="n">action</span><span class="o">=</span><span class="s1">'voom'</span><span class="p">):</span>
<span class="gp">... </span> <span class="nb">print</span><span class="p">(</span><span class="s2">"-- This parrot wouldn't"</span><span class="p">,</span> <span class="n">action</span><span class="p">,</span> <span class="n">end</span><span class="o">=</span><span class="s1">' '</span><span class="p">)</span>
<span class="gp">... </span> <span class="nb">print</span><span class="p">(</span><span class="s2">"if you put"</span><span class="p">,</span> <span class="n">voltage</span><span class="p">,</span> <span class="s2">"volts through it."</span><span class="p">,</span> <span class="n">end</span><span class="o">=</span><span class="s1">' '</span><span class="p">)</span>
<span class="gp">... </span> <span class="nb">print</span><span class="p">(</span><span class="s2">"E's"</span><span class="p">,</span> <span class="n">state</span><span class="p">,</span> <span class="s2">"!"</span><span class="p">)</span>
<span class="gp">...</span>
<span class="gp">>>> </span><span class="n">d</span> <span class="o">=</span> <span class="p">{</span><span class="s2">"voltage"</span><span class="p">:</span> <span class="s2">"four million"</span><span class="p">,</span> <span class="s2">"state"</span><span class="p">:</span> <span class="s2">"bleedin' demised"</span><span class="p">,</span> <span class="s2">"action"</span><span class="p">:</span> <span class="s2">"VOOM"</span><span class="p">}</span>
<span class="gp">>>> </span><span class="n">parrot</span><span class="p">(</span><span class="o">**</span><span class="n">d</span><span class="p">)</span>
<span class="go">-- This parrot wouldn't VOOM if you put four million volts through it. E's bleedin' demised !</span>
</pre></div>
</div>
</section>
<section id="lambda-expressions">
<span id="tut-lambda"></span><h3><span class="section-number">4.9.6. </span>Lambda 運算式<a class="headerlink" href="#lambda-expressions" title="連結到這個標頭">¶</a></h3>
<p><a class="reference internal" href="../reference/expressions.html#lambda"><code class="xref std std-keyword docutils literal notranslate"><span class="pre">lambda</span></code></a> 關鍵字用於建立小巧的匿名函式。<code class="docutils literal notranslate"><span class="pre">lambda</span> <span class="pre">a,</span> <span class="pre">b:</span> <span class="pre">a+b</span></code> 函式返回兩個引數的和。Lambda 函式可用於任何需要函式物件的地方。在語法上,它們被限定只能是單一運算式。在語義上,它就是一個普通函式定義的語法糖 (syntactic sugar)。與巢狀函式定義一樣,lambda 函式可以從包含它的作用域中引用變數:</p>
<div class="highlight-python3 notranslate"><div class="highlight"><pre><span></span><span class="gp">>>> </span><span class="k">def</span><span class="w"> </span><span class="nf">make_incrementor</span><span class="p">(</span><span class="n">n</span><span class="p">):</span>
<span class="gp">... </span> <span class="k">return</span> <span class="k">lambda</span> <span class="n">x</span><span class="p">:</span> <span class="n">x</span> <span class="o">+</span> <span class="n">n</span>
<span class="gp">...</span>
<span class="gp">>>> </span><span class="n">f</span> <span class="o">=</span> <span class="n">make_incrementor</span><span class="p">(</span><span class="mi">42</span><span class="p">)</span>
<span class="gp">>>> </span><span class="n">f</span><span class="p">(</span><span class="mi">0</span><span class="p">)</span>
<span class="go">42</span>
<span class="gp">>>> </span><span class="n">f</span><span class="p">(</span><span class="mi">1</span><span class="p">)</span>
<span class="go">43</span>
</pre></div>
</div>
<p>上面的例子用 lambda 運算式回傳了一個函式。另外的用法是傳遞一個小函式當作引數:</p>
<div class="highlight-python3 notranslate"><div class="highlight"><pre><span></span><span class="gp">>>> </span><span class="n">pairs</span> <span class="o">=</span> <span class="p">[(</span><span class="mi">1</span><span class="p">,</span> <span class="s1">'one'</span><span class="p">),</span> <span class="p">(</span><span class="mi">2</span><span class="p">,</span> <span class="s1">'two'</span><span class="p">),</span> <span class="p">(</span><span class="mi">3</span><span class="p">,</span> <span class="s1">'three'</span><span class="p">),</span> <span class="p">(</span><span class="mi">4</span><span class="p">,</span> <span class="s1">'four'</span><span class="p">)]</span>
<span class="gp">>>> </span><span class="n">pairs</span><span class="o">.</span><span class="n">sort</span><span class="p">(</span><span class="n">key</span><span class="o">=</span><span class="k">lambda</span> <span class="n">pair</span><span class="p">:</span> <span class="n">pair</span><span class="p">[</span><span class="mi">1</span><span class="p">])</span>
<span class="gp">>>> </span><span class="n">pairs</span>
<span class="go">[(4, 'four'), (1, 'one'), (3, 'three'), (2, 'two')]</span>
</pre></div>
</div>
</section>
<section id="documentation-strings">
<span id="tut-docstrings"></span><h3><span class="section-number">4.9.7. </span>說明文件字串 (Documentation Strings)<a class="headerlink" href="#documentation-strings" title="連結到這個標頭">¶</a></h3>
<p id="index-5">以下是關於說明文件字串內容和格式的慣例。</p>
<p>第一行都是一段關於此物件目的之簡短摘要。為保持簡潔,不應在這裡明確地陳述物件的名稱或型別,因為有其他方法可以達到相同目的(除非該名稱剛好是一個描述函式運算的動詞)。這一行應以大寫字母開頭,以句號結尾。</p>
<p>文件字串為多行時,第二行應為空白行,在視覺上將摘要與其餘描述分開。後面幾行可包含一或多個段落,描述此物件的呼叫慣例、副作用等。</p>
<p>Python 剖析器 (parser) 不會去除 Python 中多行字串的縮排,因此,處理說明文件的工具應在必要時去除縮排。這項操作遵循以下慣例:在字串第一行<em>之後</em>的第一個非空白行決定了整個說明文件字串的縮排量(不能用第一行的縮排,因為它通常與字串的開頭引號們相鄰,其縮排在字串文本中並不明顯),然後,所有字串行開頭處與此縮排量「等價」的空白字元會被去除。不應出現比上述縮進量更少的字串行,但若真的出現了,這些行的全部前導空白字元都應被去除。展開 tab 鍵後(通常為八個空格),應測試空白字元量是否等價。</p>
<p>下面是多行說明字串的一個範例:</p>
<div class="highlight-python3 notranslate"><div class="highlight"><pre><span></span><span class="gp">>>> </span><span class="k">def</span><span class="w"> </span><span class="nf">my_function</span><span class="p">():</span>
<span class="gp">... </span><span class="w"> </span><span class="sd">"""Do nothing, but document it.</span>
<span class="gp">...</span>
<span class="gp">... </span><span class="sd"> No, really, it doesn't do anything.</span>
<span class="gp">... </span><span class="sd"> """</span>
<span class="gp">... </span> <span class="k">pass</span>
<span class="gp">...</span>
<span class="gp">>>> </span><span class="nb">print</span><span class="p">(</span><span class="n">my_function</span><span class="o">.</span><span class="vm">__doc__</span><span class="p">)</span>
<span class="go">Do nothing, but document it.</span>
<span class="go"> No, really, it doesn't do anything.</span>
</pre></div>
</div>
</section>
<section id="function-annotations">
<span id="tut-annotations"></span><h3><span class="section-number">4.9.8. </span>函式註釋 (Function Annotations)<a class="headerlink" href="#function-annotations" title="連結到這個標頭">¶</a></h3>
<p id="index-6"><a class="reference internal" href="../reference/compound_stmts.html#function"><span class="std std-ref">函式註釋</span></a>是選擇性的元資料(metadata)資訊,描述使用者定義函式所使用的型別(更多資訊詳見 <span class="target" id="index-16"></span><a class="pep reference external" href="https://peps.python.org/pep-3107/"><strong>PEP 3107</strong></a> 和 <span class="target" id="index-17"></span><a class="pep reference external" href="https://peps.python.org/pep-0484/"><strong>PEP 484</strong></a>)。</p>
<p><a class="reference internal" href="../glossary.html#term-function-annotation"><span class="xref std std-term">註釋</span></a>以 dictionary(字典)的形式存放在函式的 <code class="xref py py-attr docutils literal notranslate"><span class="pre">__annotations__</span></code> 屬性中,且不會影響函式的任何其他部分。參數註釋的定義方式是在參數名稱後加一個冒號,冒號後面跟著一個對註釋求值的運算式。回傳註釋的定義方式是在參數列表和 <a class="reference internal" href="../reference/compound_stmts.html#def"><code class="xref std std-keyword docutils literal notranslate"><span class="pre">def</span></code></a> 陳述式結尾的冒號中間,用一個 <code class="docutils literal notranslate"><span class="pre">-></span></code> 文字接著一個運算式。以下範例註釋了一個必要引數、一個選擇性引數,以及回傳值:</p>
<div class="highlight-python3 notranslate"><div class="highlight"><pre><span></span><span class="gp">>>> </span><span class="k">def</span><span class="w"> </span><span class="nf">f</span><span class="p">(</span><span class="n">ham</span><span class="p">:</span> <span class="nb">str</span><span class="p">,</span> <span class="n">eggs</span><span class="p">:</span> <span class="nb">str</span> <span class="o">=</span> <span class="s1">'eggs'</span><span class="p">)</span> <span class="o">-></span> <span class="nb">str</span><span class="p">:</span>
<span class="gp">... </span> <span class="nb">print</span><span class="p">(</span><span class="s2">"Annotations:"</span><span class="p">,</span> <span class="n">f</span><span class="o">.</span><span class="vm">__annotations__</span><span class="p">)</span>
<span class="gp">... </span> <span class="nb">print</span><span class="p">(</span><span class="s2">"Arguments:"</span><span class="p">,</span> <span class="n">ham</span><span class="p">,</span> <span class="n">eggs</span><span class="p">)</span>
<span class="gp">... </span> <span class="k">return</span> <span class="n">ham</span> <span class="o">+</span> <span class="s1">' and '</span> <span class="o">+</span> <span class="n">eggs</span>
<span class="gp">...</span>
<span class="gp">>>> </span><span class="n">f</span><span class="p">(</span><span class="s1">'spam'</span><span class="p">)</span>
<span class="go">Annotations: {'ham': <class 'str'>, 'return': <class 'str'>, 'eggs': <class 'str'>}</span>
<span class="go">Arguments: spam eggs</span>
<span class="go">'spam and eggs'</span>
</pre></div>
</div>
</section>
</section>
<section id="intermezzo-coding-style">
<span id="tut-codingstyle"></span><h2><span class="section-number">4.10. </span>間奏曲:程式碼風格 (Coding Style)<a class="headerlink" href="#intermezzo-coding-style" title="連結到這個標頭">¶</a></h2>
<p id="index-9">現在你即將要寫更長、更複雜的 Python 程式,是時候討論一下<em>編碼樣式</em>了。大多數語言都能以不同的樣式被書寫(或更精確地說,被<em>格式化</em>),而有些樣式比其他的更具可讀性。能讓其他人輕鬆閱讀你的程式碼永遠是一個好主意,而使用優良的編碼樣式對此有極大的幫助。</p>
<p>對於 Python,大多數的專案都遵循 <span class="target" id="index-18"></span><a class="pep reference external" href="https://peps.python.org/pep-0008/"><strong>PEP 8</strong></a> 的樣式指南;它推行的編碼樣式相當可讀且賞心悅目。每個 Python 開發者都應該花點時間研讀;這裡是該指南的核心重點:</p>
<ul>
<li><p>用 4 個空格縮排,不要用 tab 鍵。</p>
<p>4 個空格是小縮排(容許更大的巢套深度)和大縮排(較易閱讀)之間的折衷方案。Tab 鍵會造成混亂,最好別用。</p>
</li>
<li><p>換行,使一行不超過 79 個字元。</p>
<p>換行能讓使用小顯示器的使用者方便閱讀,也可以在較大顯示器上並排陳列多個程式碼檔案。</p>
</li>
<li><p>用空行分隔函式和 class(類別),及函式內較大塊的程式碼。</p></li>
<li><p>如果可以,把註解放在單獨一行。</p></li>
<li><p>使用說明字串。</p></li>
<li><p>運算子前後、逗號後要加空格,但不要直接放在括號內側:<code class="docutils literal notranslate"><span class="pre">a</span> <span class="pre">=</span> <span class="pre">f(1,</span> <span class="pre">2)</span> <span class="pre">+</span> <span class="pre">g(3,</span> <span class="pre">4)</span></code>。</p></li>
<li><p>Class 和函式的命名樣式要一致;按慣例,命名 class 用 <code class="docutils literal notranslate"><span class="pre">UpperCamelCase</span></code>(駝峰式大小寫),命名函式與 method 用 <code class="docutils literal notranslate"><span class="pre">lowercase_with_underscores</span></code>(小寫加底線)。永遠用 <code class="docutils literal notranslate"><span class="pre">self</span></code> 作為 method 第一個引數的名稱(關於 class 和 method,詳見 <a class="reference internal" href="classes.html#tut-firstclasses"><span class="std std-ref">初見 class</span></a>)。</p></li>
<li><p>若程式碼是為了用於國際環境時,不要用花俏的編碼。Python 預設的 UTF-8 或甚至普通的 ASCII,就可以勝任各種情況。</p></li>
<li><p>同樣地,若不同語言使用者閱讀或維護程式碼的可能性微乎其微,就不要在命名時使用非 ASCII 字元。</p></li>
</ul>
<p class="rubric">註解</p>
<aside class="footnote-list brackets">
<aside class="footnote brackets" id="id2" role="doc-footnote">
<span class="label"><span class="fn-bracket">[</span><a role="doc-backlink" href="#id1">1</a><span class="fn-bracket">]</span></span>
<p>實際上,<em>傳址呼叫 (call by object reference)</em> 的說法可能較為貼切。因為,若傳遞的是一個可變物件時,呼叫者將看得見被呼叫者對物件做出的任何改變(例如被插入 list 內的新項目)。</p>
</aside>
</aside>
</section>
</section>
<div class="clearer"></div>
</div>
</div>
</div>
<div class="sphinxsidebar" role="navigation" aria-label="Main">
<div class="sphinxsidebarwrapper">
<div>
<h3><a href="../contents.html">目錄</a></h3>
<ul>
<li><a class="reference internal" href="#">4. 深入了解流程控制</a><ul>
<li><a class="reference internal" href="#if-statements">4.1. <code class="xref std std-keyword docutils literal notranslate"><span class="pre">if</span></code> 陳述式</a></li>
<li><a class="reference internal" href="#for-statements">4.2. <code class="xref std std-keyword docutils literal notranslate"><span class="pre">for</span></code> 陳述式</a></li>
<li><a class="reference internal" href="#the-range-function">4.3. <code class="xref py py-func docutils literal notranslate"><span class="pre">range()</span></code> 函式</a></li>
<li><a class="reference internal" href="#break-and-continue-statements">4.4. <code class="xref std std-keyword docutils literal notranslate"><span class="pre">break</span></code> 和 <code class="xref std std-keyword docutils literal notranslate"><span class="pre">continue</span></code> 陳述式</a></li>
<li><a class="reference internal" href="#else-clauses-on-loops">4.5. 迴圈的 <code class="xref std std-keyword docutils literal notranslate"><span class="pre">else</span></code> 子句</a></li>
<li><a class="reference internal" href="#pass-statements">4.6. <code class="xref std std-keyword docutils literal notranslate"><span class="pre">pass</span></code> 陳述式</a></li>
<li><a class="reference internal" href="#match-statements">4.7. <code class="xref std std-keyword docutils literal notranslate"><span class="pre">match</span></code> 陳述式</a></li>
<li><a class="reference internal" href="#defining-functions">4.8. 定義函式 (function)</a></li>
<li><a class="reference internal" href="#more-on-defining-functions">4.9. 深入了解函式定義</a><ul>
<li><a class="reference internal" href="#default-argument-values">4.9.1. 預設引數值</a></li>
<li><a class="reference internal" href="#keyword-arguments">4.9.2. 關鍵字引數</a></li>
<li><a class="reference internal" href="#special-parameters">4.9.3. 特殊參數</a><ul>
<li><a class="reference internal" href="#positional-or-keyword-arguments">4.9.3.1. 位置或關鍵字引數 (Positional-or-Keyword Arguments)</a></li>
<li><a class="reference internal" href="#positional-only-parameters">4.9.3.2. 僅限位置參數 (Positional-Only Parameters)</a></li>
<li><a class="reference internal" href="#keyword-only-arguments">4.9.3.3. 僅限關鍵字引數 (Keyword-Only Arguments)</a></li>
<li><a class="reference internal" href="#function-examples">4.9.3.4. 函式範例</a></li>
<li><a class="reference internal" href="#recap">4.9.3.5. 回顧</a></li>
</ul>
</li>
<li><a class="reference internal" href="#arbitrary-argument-lists">4.9.4. 任意引數列表 (Arbitrary Argument Lists)</a></li>