博客
关于我
强烈建议你试试无所不能的chatGPT,快点击我
一个“MacBook”新手的Python“笨办法”自学之旅 #第九章:Python的函数
阅读量:6894 次
发布时间:2019-06-27

本文共 15324 字,大约阅读时间需要 51 分钟。

第九章:Python的函数function

 

   ---------------------------------<习题18&19:命名、变量、代码、函数>------------------------------

   

   除了Python自带的函数外,你还可以在Python环境下定义自己的函数,没错,是可以创造自己的函数。这个函数可以接受参数,方式跟我们前面学到的一样,可以用raw_input()或argv。

   命令def:它的意思是“定义define”,如同定义变量一样,定义函数也是用“def”这个命令;

   在def后面,空一格,然后键入函数的名称(你可以自由选择,但最好是能体现函数的功能,和变量的取名一样,不能用数字,但可以用字幕开头的名字,例如a1),再然后用“冒号:" 来收尾,表面下面的内容是该函数的内容;冒号后另起一行,需要使用4个空格缩进,表示缩进的代码是被包含在上面定义的函数内部。

   下面展示书中四个函数的例子,ex18.py的代码如下:

1 #-*-coding:utf-8-*- 2  3 # this one is like your scripts with argv 4 def print_two(*args): #def 是命令define的缩写,定义的意思。此处用来定义一个函数print_two(), 5                       #后面的冒号,表示冒号后面的内容,是该函数的内容,即该函数是一个输出字符串的函数 6     arg1, arg2 = args 7     print "arg1: %r, arg2: %r" % (arg1, arg2) 8      9 # ok, that *args is actully pointless, we can just do this10 def print_two_again(arg1, arg2): #相对于第一个函数,没有使用参数解包的过程,11                                  #而是直接在函数的括号内输入变量名12     print "arg1: %r, arg2: %r" % (arg1, arg2)13     14 # this just takes one argument15 def print_one(arg1):16     print "arg1: %r" % arg117     18 # this one takes no arguments19 def print_none():20     print "I got nothing'."21     22 23 # 下面四行代码,是为了运行上面的四个函数,直接键入函数的名称,并在函数的括号内写入该函数的参数即可    24 print_two("Zed", "Shaw")25 print_two_again("Zed", "Shaw")26 print_one("First!")27 print_none()
ex18.py

   终端运行结果如下:

   

 

   注意:请一定要将函数相关的定义和使用弄清楚,因为可能会跟后吗学到的“类class”弄混,我现在也不能完完全全地讲出这两则的区别,希望再学到“类class”的时候会弄清楚,届时会针对函数和类的区别做一个解释

 

   在习题19中,书中讲到几种函数的参数传递方式,ex19.py代码如下:

1 #-*-coding:utf-8-*- 2 def cheese_and_crackers(cheese_count, boxes_of_crackers): 3     print "You have %d cheeses!" % cheese_count 4     print "You have %d boxes of crackers!" % boxes_of_crackers 5     print "Man that's enough for a party!" 6     print "Get a blanket.\n" 7  8  9 print "We can just give the founction numbers directly:"10 cheese_and_crackers(20, 30) #直接用数值赋予函数的输入11 12 13 print "OR, we can use variables from our script:"14 amount_of_cheese = 10  #该变量在此时赋予的数值,可运用于其它相同的变量名的值,15 amount_of_crackers = 50  #该变量在此时赋予的数值,可运用于其它相同的变量名的值,16 17 cheese_and_crackers(amount_of_cheese, amount_of_crackers) #利用已被赋予数值的变量,作为函数的输入18 19 20 print "We can even do math inside too:"21 cheese_and_crackers(10+20, 5+6) #可以用算式作为函数的输入22 23 24 print "And we can combine the two, variables and math:"25 cheese_and_crackers(amount_of_cheese +100, amount_of_crackers + 1000) #可以用字符串和数字的和,作为函数的输入参数
ex19.py

   终端运行结果如下:

   

   

   我自己也用两种不同的方式,完成函数参数的传递:raw_input()和argv

   ex19_2.py用的是raw_input(), 我就不在贴上终端运行结果了:

1 # -*-coding:utf-8-*- 2 # 不好意思,我在辞职之前,是建筑公司的一名电气工程师,平时会涉及到电缆cable数量的统计工作,于是 3 #    就写了下面这个脚本。 4  5 print "we can use raw_input() for inputing all the arguments" 6 print "Now you can type in your arguments" 7  8 print "How many zones there are ?" 9 zones = int(raw_input()) #将输入的str强制转换成int,与第25行的变量要求一致10 11 print "How many levels each zones?"12 levels = int(raw_input())13 14 print "How many layouts in each levels?"15 layouts = int(raw_input())16  17 print "How many types of cables in each layouts?"18 types = int(raw_input())19 20 print "The quantity of each kind of cable:" 21 quantities = int(raw_input())22 23 def len_cables(zones, levels, layouts, types, quantities):24 # 函数名和函数的参数的定义,注意括号和最后的冒号25     length_cables = zones * levels * layouts * types * quantities26     print "There are %d zones in project Thalassa" % zones27     print "Each zone has %d levels" % levels28     print "Each level has %d layouts" % layouts29     print "Each layout has %d types of cables" % types30     print "Each type of cables has %d meters" % quantities31     print "The length of cables equals %d" % length_cables32     # 函数的参数必须是4个空格的缩进33 34 35 len_cables(zones, levels, layouts, types, quantities)
ex19_2.py

   ex19_3.py用的是argv,值得注意的是,这里函数的参数的类型和变量的类型产生冲突,为了解决,我使用了int()将字符串强制转换成数值类型,详情见代码:

1 # -*-coding:utf-8-*- 2  3 print "We can use argv to input the arguments:" 4   5 from sys import argv 6  7 name, zones, levels, layouts, types, quantities = argv 8  9 10 11 def len_cables(zones, levels, layouts, types, quantities):12 # 函数名和函数的参数的定义,注意括号和最后的冒号13     length_cables = int(zones) * int(levels) * int(layouts) * int(types) * int(quantities)14 15     print "the name of project is %s" %name # 因为输出的是字符串,所以不能用%d,而应该用%r或%s16     print "There are %r zones in project Thalassa" % zones17     print "Each zone has %r levels" % levels18     print "Each level has %r layouts" % layouts19     print "Each layout has %r types of cables" % types20     print "Each type of cables has %r meters" % quantities21     print "The length of cables equals %r" % length_cables22     # 函数的参数必须是4个空格的缩进23     24 len_cables(zones, levels, layouts, types, quantities)25 26 #因为在第13行中,各个参数的的乘积得到变量length_cables的定义,因此length_cables的输出应该是数字,而非字符串27 #但是在第24行中,虽然我们在输入这些参数时候输入的是数字,但是系统默认为其属性是字符串28 #因此关于这5个参数的定义,在第13行和第24行产生冲突,29 #会出现TypeError: can't multiply sequence by non-int of type 'str'30 #所以在第13行,给每一个参数强制转换成int,而非str
ex19_3.py

 

 

---------------------------------------<习题20:函数和文件>-----------------------------------

   

   这个习题讲的是将函数和文件的读取结合起来。除此之外,还有一个很重要的命令:f.seek(1, 0):

   # f.seek(p,0) 将指针移动当文件第p个字节处,绝对位置

   # f.seek(p,1) 将指针移动到相对于当前位置之后的p个字节
   # f.seek(p,2) 将指针移动到相对文章尾之后的p个字节

   我准备的待读取文件ex20_sample.txt如下:

1  "I don't know what's in her mind." 2 'Maybe I am the the unimportant one.' 3 'It does not change anything with me or not.' 4 'So I should put myself in the right position.' 5 'Also about my demands.'
ex20_sample.txt

   

   见ex20.py的代码:

1 #-*-coding:utf-8-*- 2  3 from sys import argv # 从sys软件包中调取参数变量argv使用 4  5 script, input_file = argv # argv解包 6  7 def print_all(f): # 定义函数print_all(),f仅仅是个变量的名字 8     print f.read() # 函数的内容是输出文本f的内容 9     10 def rewind(f): # 定义函数rewind(f),f仅仅是个变量的名字11     f.seek(1,0) # 该函数的作用如下:1表示从文本开始的第1个字节的位置。12                 # 这个数字只影响第一个line_count的位置13     # f.seek(p,0) 将指针移动当文件第p个字节处,绝对位置14     # f.seek(p,1) 将指针移动到相对于当前位置之后的p个字节15     # f.seek(p,2) 将指针移动到相对文章尾之后的p个字节16     17     18 def print_a_line(line_count, f): # 定义函数print_a_line19     print line_count, f.readline() #即为输出该行在文本中是第几行,而且把该行读出来20     #此处的line_count与下面的current_line是函数print_a_line的第一个参数,line_count只起到象征作用21     #而下面的current_line是经过定义的22     #readline()函数返回的内容中包含文件本来就有一个\n,而print在打印时又会添加一个\n,这样就会多一出一个空行,23     #解决方法是在print语句结尾加一个逗号24     25 current_file = open(input_file) # 定义current_file,为什么在argv的时候不用一样的变量名呢?26 # 因为input_file仅仅是个参数,其属性是一个文本的名称(字符串),而current_file是个变量,其属性为一个txt文本27 28 print "First let's print the whole file:\n"29 30 print_all(current_file)31 print "-" * 3032 33 print "Now, let's rewind, kind of like a tape."34 35 rewind(current_file)36 37 print "Let's print five lines:"38 39 40 current_line1 = 1 #定义第一个current_line的值为1,表示文本的第一句话前面标注“1”41 print_a_line(current_line1, current_file) 42 43 current_line2 = current_line1 + 2 #定义第二个current_line的值为第一个current_line +2,44                                 #表示文本的第一句话前面标注“1”45 print_a_line(current_line2, current_file)46 47 current_line3 = current_line2 + 148 print_a_line(current_line3, current_file)49 50 current_line4 = current_line3 + 151 print_a_line(current_line4, current_file)52 53 current_line5 = current_line4 + 154 print_a_line(current_line5, current_file)
ex20.py

   终端运行结果如下:

   

 

 

   在ex20.py的最后一段代码,是打印输出文件的每一行,我在第八章里的ex15_3.py脚本也用4种方法达到同样的效果,但是源代码里面比较复杂,我将它改善了,见代码ex20_1.py:

1 #-*-coding:utf-8-*- 2  3 from sys import argv # 从sys软件包中调取参数变量argv使用 4 from sys import exit 5  6 script, input_file = argv # argv解包 7  8 def print_all(f): # 定义函数print_all(),f仅仅是个变量的名字 9     print f.read() # 函数的内容是输出文本f的内容10     11 def rewind(f): # 定义函数rewind(f),f仅仅是个变量的名字12     f.seek(1,0) # 该函数的作用如下:将指针放到第一个字节的位置。1表示从文本开始的第1个字节的位置。13                 # 这个数字只影响第一个line_count的位置14     # f.seek(p,0) 将指针移动当文件第p个字节处,绝对位置15     # f.seek(p,1) 将指针移动到相对于当前位置之后的p个字节16     # f.seek(p,2) 将指针移动到相对文章尾之后的p个字节17     18     19 def print_a_line(line_count, f): # 定义函数print_a_line20     print line_count, f.readline() #即为输出该行在文本中是第几行,而且把该行读出来21     #此处的line_count与下面的current_line是函数print_a_line的第一个参数,line_count只起到象征作用22     #而下面的current_line是经过定义的23     #readline()函数返回的内容中包含文件本来就有一个\n,而print在打印时又会添加一个\n,这样就会多一出一个空行,24     #解决方法是在print语句结尾加一个逗号25     26 current_file = open(input_file) # 定义current_file,为什么在argv的时候不用一样的变量名呢?27 # 因为input_file仅仅是个参数,其属性是一个文本的名称(字符串),而current_file是个变量,其属性为一个txt文本28 29 print "First let's print the whole file:\n"30 31 print_all(current_file)32 print "-" * 3033 34 print "Now, let's rewind, kind of like a tape."35 36 rewind(current_file)37 38 print "-"*3039 40 41 42 print "Let's print five lines:"43 def line(current_line):44     45     while current_line <=4: #此处的变量current_line默认已经被定义46     47         current_line = current_line + 148         print "This is No%r line:" % current_line49         print_a_line(current_line, current_file)50         51         line(current_line)52     else:53         exit(0)54 55 line(0)
ex20_1.py

   终端运行结果如下:

   

 

---------------------------------------<习题21&24:函数和文件>-----------------------------------

   

   我在网上查了很多关于命令return的原理,但是都没有看的很明白。我自己的理解是:return命令将某个值或者变量返回,供用户随时调用,例如将函数的结果定义成一个变量。

   大家先看一下ex21.py的代码:

1 #-*-coding:utf-8-*- 2  3 def add(a, b): 4     print "ADDING %d + %d" %(a, b) # 该命令行只是解释函数的内容是什么 5     return a + b #该命令行是函数实际的输出结果 ,在该函数外就可以调取该结果,其形式为add(a, b) 6     # 以上两行统一定义了函数add 7      8 def subtract(a, b): 9     print "SUBTRACTING %d - %d" % (a, b)10     return a - b11 12 def multiply(a, b):13     print "MUTIPLY %d * %d" %(a, b)14     return a * b15     16 def divide(a, b): #不要忘记了冒号17     print "DIVIDING %d / %d" %(a, b)18     return a / b19     20 21 print "Let's do some math wiht just fonctions."22 23 age = add(30, 5)24 height = subtract(78, 4)25 weight = multiply(90, 2)26 iq = divide(100, 2)27 28 29 print "Age: %d, Height: %d, Weight: %d, IQ: %d" %(age, height, weight, iq)30 31 32 # A puzzle for the extra credit, type it in anyway.33 print "Here is a puzzle."34 35 what = add(age, subtract(height, multiply(weight, divide(iq, 2))))36 37 print "That becomes:" , what, "Can you do it by hand?"38  # 也可以不用强制转换符%,输出变量what的值。如果使用%, 变量前面的逗号需要删除
ex21.py

   终端运行结果如下:

   

 

   关于return的命令,我自己写了一个代码,可供参考:

1 #-*-coding:utf-8-*- 2 # 用到return的 3 def add(a, b): 4    return a + b 5     6 print add(2, 3) #不需要再运行函数,此时的add(2, 3)就是一个变量,直接可以打印输出的结果为5 7  8  9 # 未用到return的10 def add2(a, b):11     c = a + b12     print c13 add2(2, 3) # 需要运行一下函数,在函数内部,已经有了打印输出的命令
return.py

 

   下面介绍一下习题24,一个比较特殊的地方:介绍函数返回多个数值时,这些数值如何被重新定义和被调用:

1 #-*-coding:utf-8-*- 2 print "Let's practice everthing!" 3 print 'You\'d need to know \'bout escapes with \\ that do \n newlines and \t tabs.' 4  5 poem = """ 6 \tThe lovely world  7 with logic so firmly planted 8 cannot discern \n the needs of love 9 nor comprehend passion from institution10 and requires an explantation\n\t\twhere there is none.11 """12 # 一个\t表示空出8位;13 print "----------"14 print poem15 print "----------"16 17 five = 10 - 2 + 3  - 618 print "This should be five :%s" % five19 20 def secret_formula(started):21     jelly_beans = started * 50022     jars = jelly_beans / 100023     crates = jars / 10024     return jelly_beans, jars, crates25     26     27     28 start_point = 1000029 beans, jars, crates = secret_formula(start_point)30 #该命令行是为了将函数 secret_formula(start_point)的三个返回值定义给三个变量jelly_beans, jars, crates31 # 此处的beans等于上面的jelly_beans,不是因为名字相似,而是因为重新定义了函数secret_formula的第一个返回值32 # 同理可知,第二个和第三个的参数,也是对应的,在此处可以随便更改33 34 print "\t\tWith a starting point of : %d" %start_point35 print "We'd have %d beans, %d jars, and %d crates." %(beans, jars, crates) #调用函数的返回值36 37 start_point = start_point / 1038 39 print "We can also do that this way:"40 print "We'd have %d beans, %d jars, and %d crates.." % secret_formula(start_point)# 该方法也可以调用函数的返回值 41 # 可以用这个方法,%函数名,即可转换函数的返回值
ex24.py

 

   

--------------------------------------<习题25:在终端直接调用函数>----------------------------------

   

   我们之前讲的这么多习题,都是用TextWrangler编辑好Python脚本,然后在终端里输入“python ex.py"来运行该脚本。其实我们可以在终端路直接调用某个脚本中的函数,在介绍如何操作之前,先介绍几个比较特殊的函数:split(), pop(), sorted()。它们的功能,在ex25.py中有非常详细的介绍:

  例如 ex25.py代码如下:

1 #-*-coding:utf-8-*- 2 # 用脚本编写函数,写出的函数,在python环境下可以调用 3 def break_words(stuff): 4     """This function will break up words for us.""" # 这段命令行,为“帮助文档”,在python运行时,执行help(ex25) 5                                                     # 或者help(ex25.break_words)会显示出来,起到注释的作用 6     words = stuff.split(' ') # split命令,可以将对象分离,形式是'1’,‘2’ 7     return words # 返回words的值,用于调用 8  9 def sort_words(words):  #是一个给句子排序的命令10     """Sorts the words."""11     return sorted(words) 12 13 def print_first_word(words):14     """Prints the first word after popping it off."""15     word = words.pop(0) # pop()函数用于移除列表中的一个元素(默认为最后一个元素),并且返回该元素的值16                         # 0 表示是列表中的第一个元素,1 表示第二个,以此类推,最后一个也可以用-117     print word # 此处返回的第一个元素,仍是第一个函数中返回的列表words中的第一个元素,因为第二个函数中的words未用return返回18     # 运行完上函数后,序列words的第一个元素ALl被删除掉了19     20 def print_last_word(words):21     """Prints the last word after popping it off."""22     word = words.pop(-1)23     print word # 此处返回的最后一个元素,仍是第一个函数中返回的列表words中的最后一个元素,因为第二个函数中的words未用return返回24     # 运行完上函数后,序列words的最后一个元素wait被删除掉了,第一个元素All在上一个函数中删除了25     26 def sort_sentence(sentence):27     """Takes in a full sentence and returns the sorted words."""28     words = break_words(sentence)29     return sort_words(words)30     31 def print_first_and_last(sentence):32     """Prints the first and last words of the sentence."""33     words = break_words(sentence)34     print_first_word(words)35     print_last_word(words)36     37 def print_first_and_last_sorted(sentence):38     """Sorts the words then prints the first and last one."""39     words = sort_sentence(sentence)40     print_first_word(words)41     print_last_word(words)
ex25.py

   终端运行结果如下:注意下方的截屏抬头是“python”,而之前所有的截屏抬头都是“bash”

   

   截屏无法解释在python环境下键入的每一行代码的含义,下方是我在TextWrangler把终端运行结果又解释了一下,供参考:

1 #下面是在bash环境下运行python: 2   3 # >>> import ex25 该命令是在python中调用脚本ex25,在python环境下,不需要带.py的后缀。 4 # >>> sentence = "All good things come to those who waits!" 5 # >>> words = ex25.break_words(sentence) 调用ex25中的第一个函数,对象是上面定义的sentence。这段命令 6                                          #中的ex25.break_words()中的“.”是为了告诉python:”嗨, 7                                          #,我要运行ex25里面的那个交break_words()的函数 8 # >>> words :是输入变量words, 即在python环境下,打印出ex25.break_words()的返回值words 9 # ['All', 'good', 'things', 'come', 'to', 'those', 'who', 'waits!']10 # >>> sorted_words = ex25.sort_words(words) 是在python环境下定义变量sorted_words供后面使用11 # >>> sorted_words 12 # ['All', 'come', 'good', 'things', 'those', 'to', 'waits!', 'who']13 # >>> ex25.print_first_word(words)14 # All15 # >>> ex25.print_last_word(words)16 # waits!17 # >>> wrods18 # Traceback (most recent call last):19   # File "
", line 1, in
20 # NameError: name 'wrods' is not defined21 # >>> words22 # ['good', 'things', 'come', 'to', 'those', 'who']23 # >>> ex25.print_first_word(sorted_words) 此处的sorted_words并不在脚本当中,但是在python环境下已经定义,24 # sorted_words = ex25.sort_words(words)25 # All26 # >>> ex25.print_last_word(sorted_words)27 # who28 # >>> sorted_words29 # ['come', 'good', 'things', 'those', 'to', 'waits!']30 # >>> sorted_words = ex25.sort_sentence(sentence)31 # >>> sorted_words32 # ['All', 'come', 'good', 'things', 'those', 'to', 'waits!', 'who']33 # >>> ex25.print_first_and_last(sentence)34 # All35 # waits!36 # >>> ex25.print_first_and_last_sorted(sentence)37 # All38 # who
ex25_terminal

 

   以上便是对Python函数的介绍,有不清楚之处,还请见谅,本人能力有限!

 

第十章预告:逻辑关系、布尔表达式、if/elif/else语句、循环for语句、while语句、列表及其相关

 

   

转载于:https://www.cnblogs.com/la-route-d-ingenieur/p/11044511.html

你可能感兴趣的文章
LeetCode 题库练习 2
查看>>
iframe自适应高度(转)
查看>>
【windows】环境下mysql的数据备份以及恢复
查看>>
ABP源码分析二十四:Notification
查看>>
Python操作记录
查看>>
Photo4
查看>>
Java的NIO
查看>>
【 D3.js 入门系列 — 1 】 第一个程序 HelloWorld
查看>>
Problem 1024 - Easy Job
查看>>
(八)mybatis之多对多
查看>>
h5空白页面过渡加载
查看>>
[POJ]1164 The Castle
查看>>
Android Dialog
查看>>
request.getRequestURL()和request.getRequestURI()的区别
查看>>
十四、python开发之面向对象
查看>>
HTML笔记04---计时事件
查看>>
【UOJ117】 欧拉回路(欧拉回路)
查看>>
eclipse 工具在工作中实用方法
查看>>
PhysX 3.2中RAW格式文件的解析
查看>>
Spring返回jsp页面
查看>>