每天一小时python官方文档学习(三)————函数

上一天看到第四章的一半,介绍了一些常用的流程控制工具,也就是常用语句,主要是ifforrange()breakcontinueelsepass。今天把第四章剩下的看完,讲的是如何在python中定义和使用函数。函数其实就是一种对代码的封装,对于一段完成某种功能的代码,如果需要在程序中多次用到这个功能,不使用函数的话,就要写多次相同的代码,很麻烦;如果使用函数的话,定义函数只需要一次,往后每次需要使用这个函数的话调用就行了,即实现了代码重用,简便很多。

4.6. 定义函数

python中,我们使用关键字 def 引入一个函数定义。它必须后跟函数名称带括号的形式参数列表。构成函数体的语句从下一行开始,并且必须缩进

函数体的第一个语句通常是注释或者帮助文档,用三引号‘’‘ ’‘’括起来,里面应该写上函数的功能和各参数的意义等等,是面向用户的。在notebook里面使用help()就可以查看到这些信息。写帮助文档是一个应该养成的好习惯。

函数调用执行)则是直接运行函数名,如果有参数则写在括号内,一个用于输出斐波拉契数列的函数例子如下:

>>> def fib(n):    # 函数定义
...     """函数功能:打印n以内的斐波拉契数列"""
...     a, b = 0, 1
...     while a < n:
...         print(a, end=' ')
...         a, b = b, a+b
...     print()
...
>>> # 函数调用
... fib(2000)
0 1 1 2 3 5 8 13 21 34 55 89 144 233 377 610 987 1597

定义了的函数是一个特定的类型,它也支持重命名,如下f和fib就是同一个函数了:

>>> fib
<function fib at 10042ed0>
>>> f = fib
>>> f(100)
0 1 1 2 3 5 8 13 21 34 55 89

学过其他语言的人可能会问,python的函数有返回值吗?答案是肯定的,我们可以用return语句返回指定的值,如果像上面的例子一样没有return呢?实际上也有返回值,只不过是一个None而已,使用print()就可以看到它了。

总结一句:return 语句会从函数内部返回一个值。 不带表达式参数的 return 会返回 None。 函数执行完毕退出也会返回 None

>>> fib(0)
>>> print(fib(0))
None

最后我们改写上面的斐波拉契函数,不是直接打印print(),而是先调用函数返回return一个列表,再打印这个列表:

>>> def fib2(n):  # 函数定义
...     """函数功能:返回一个列表,里面包含了n以内的斐波拉契数列"""
...     result = []
...     a, b = 0, 1
...     while a < n:
...         result.append(a)    # 向列表新增一个数据
...         a, b = b, a+b
...     return result
...
>>> f100 = fib2(100)    # 函数调用
>>> f100                # 打印结果
[0, 1, 1, 2, 3, 5, 8, 13, 21, 34, 55, 89]

4.7. 函数定义的更多形式

4.7.1. 参数默认值

最有用的形式是对一个或多个参数指定一个默认值。这样创建的函数,可以用比定义时允许的更少的参数调用,比如:

def ask_ok(prompt, retries=4, reminder='Please try again!'):while True:ok = input(prompt)if ok in ('y', 'ye', 'yes'): # in关键字可以测试一个序列是否包含某个值return Trueif ok in ('n', 'no', 'nop', 'nope'):return Falseretries = retries - 1if retries < 0:raise ValueError('invalid user response')print(reminder)

这个函数可以通过几种方式调用:

  • 只给出必需的参数(参数prompt):ask_ok('Do you really want to quit?')
  • 给出一个可选的参数(参数prompt和retries):ask_ok('OK to overwrite the file?', 2)
  • 或者给出所有的参数(参数prompt、retries和reminder):ask_ok('OK to overwrite the file?', 2, 'Come on, only yes or no!')

有两点需要注意!!

一、默认值是在 定义过程 中在函数定义处计算的,所以以下结果会打印5而不是6:

i = 5def f(arg=i):   # 此处传入默认值i,所以arg=i=5print(arg)i = 6  # 不影响f的默认值
f()

二、默认值只会执行一次。这条规则在默认值为可变对象(列表、字典以及大多数类实例)时很重要。比如,下面的函数会存储在后续调用中传递给它的参数:

def f(a, L=[]):L.append(a)return Lprint(f(1))
print(f(2))
print(f(3))

打印结果为:

[1]
[1, 2]
[1, 2, 3]

如果你不想要在后续调用之间共享默认值,你可以这样写这个函数:

def f(a, L=None):if L is None:L = []L.append(a)return L

打印结果为:

[1]
[2]
[3]

4.7.2. 关键字参数

4.7.3. 特殊参数

这两节已经在我之前的文章中介绍过了,感兴趣的小伙伴可以去看看:
python函数参数那些事,关键字参数与位置参数

4.7.4. 任意的参数列表

最后,最不常用的选项是可以使用任意数量的参数调用函数。这些参数会被包含在一个元组里(参见 元组和序列 )。在可变数量的参数之前,可能会出现零个或多个普通参数。:

def write_multiple_items(file, separator, *args):file.write(separator.join(args))

一般来说,这些可变参数 将在形式参数列表的末尾,如上面代码中的*args参数(和C语言区分一下,注意不是指针)。因为它们收集传递给函数的所有剩余输入参数,简单来说,就是捡破烂的,剩下的参数都归他了。
但也有例外,它不在参数列表的末尾。此时,出现在 *args 参数之后的任何形式参数都是 仅关键字参数,也就是说它们只能作为关键字参数而不能是位置参数:

>>> def concat(*args, sep="/"):
...     return sep.join(args)
...
>>> concat("earth", "mars", "venus")
'earth/mars/venus'
>>> concat("earth", "mars", "venus", sep=".")
'earth.mars.venus'

4.7.5. 解包参数列表

如果我们的参数已经在列表或元组里了,但是想把里面的元素作为单独的参数传入函数,应该怎么做呢?此时称为对参数列表进行解包
例如,内置的 range() 函数需要单独的 startstop 参数。如果它们不能单独使用,可以使用 *操作符 来编写函数调用以便从列表或元组中解包参数:

>>> list(range(3, 6))      #正常的调用,向range函数传入两个单独的参数3和6
[3, 4, 5]
>>> args = [3, 6]
>>> list(range(*args))    #解包调用,从列表args中解包出数字3和6,再传入range函数
[3, 4, 5]

如果参数在字典里,则用**操作符解包出字典的值value,来提供关键字参数:

>>> def parrot(voltage, state='a stiff', action='voom'):
...     print("-- This parrot wouldn't", action, end=' ')
...     print("if you put", voltage, "volts through it.", end=' ')
...     print("E's", state, "!")
...
>>> d = {"voltage": "four million", "state": "bleedin' demised", "action": "VOOM"}
>>> parrot(**d)
-- This parrot wouldn't VOOM if you put four million volts through it. E's bleedin' demised !

4.7.6. Lambda 表达式

可以用 lambda 关键字来创建一个小的匿名函数。Lambda函数可以在需要函数对象的任何地方使用。它们在语法上限于单个表达式。从语义上来说,它们只是正常函数定义的语法糖。与嵌套函数定义一样,lambda函数可以引用所包含域的变量
简单来说,Lambda函数有两个作用:返回一个函数,或者传递一个小函数作为参数
作用1:

>>> def make_incrementor(n):
...     return lambda x: x + n
...
>>> f = make_incrementor(42)
>>> f(0)
42
>>> f(1)
43

作用2:

>>> pairs = [(1, 'one'), (2, 'two'), (3, 'three'), (4, 'four')]
>>> pairs.sort(key=lambda pair: pair[1])
>>> pairs
[(4, 'four'), (1, 'one'), (3, 'three'), (2, 'two')]

4.7.7. 文档字符串

4.7.8. 函数标注

这两节介绍的是关于函数帮助文档和注释内容和格式的一些约定,这里不详细展开了。

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.mzph.cn/news/307741.shtml

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

leetcode452. 用最少数量的箭引爆气球

一:论语 少些自我感动&#xff0c;多谢反思&#xff0c;时刻警惕自己是否在假装很努力&#xff0c;自己懂不懂 自己会不会 自己想要什么 只有自己 最清楚 二&#xff1a;题目 三:上码 class Solution { public:/**思路:1.这道题类似无重叠空间,我们先按每个气球的右边界升序…

ASP.NET Core 3.x启动时运行异步任务(一)

这是一个大的题目&#xff0c;需要用几篇文章来说清楚。这是第一篇。一、前言在我们的项目中&#xff0c;有时候我们需要在应用程序启动前执行一些一次性的逻辑。比方说&#xff1a;验证配置的正确性、填充缓存、或者运行数据库清理/迁移等。如何合理、有效、优雅地完成这个任务…

每天一小时python官方文档学习(四)————数据结构之列表

终于进入到第五章数据结构部分了&#xff0c;python中常用的容器有列表、元组、集合和字典&#xff0c;今天主要了解的是最为常用的列表。 5. 数据结构 5.1. 列表的更多特性 对于列表的操作有很多&#xff0c;具体操作看官方文档就行&#xff0c;但是我们对列表有什么操作&a…

leetcode435. 无重叠区间

一&#xff1a;论语 道不同 不相为谋 我们没有理由拿着自己的评判标准 去看待别人所经历的事情&#xff0c;重来就没有真正的感同身受&#xff0c;我们能做的就是尊重他人的看法 &#xff0c;保留自己的态度。 二&#xff1a;题目 三:上码 class Solution { public:/**思路:…

Swagger扩展为你添油加气

关注架构师高级俱乐部开启架构之路不定期福利发放哦~Leon读完需要4分钟速读仅需 2 分钟介绍一款Swagger扩展日常接口开发中都需要用到Swagger来生成接口文档并用 Swagger 自带支持的模拟请求进行测试&#xff0c;但是需要支持认证或者上传文件等操作需要自行去按接口进行开发才…

leetcode763. 划分字母区间

一&#xff1a;论语 保留自己的态度&#xff0c;尊重别人的看法&#xff0c;不强迫别人按照自己的意愿做事。 二:题目 三:上码 class Solution { public:vector<int> partitionLabels(string s) {/**思路:1.在这里我们选取的数据结构是map容器,我们只要下记录每个字母…

每天一小时python官方文档学习(五)————数据结构之元组、集合与字典

昨天介绍完了最常用的列表&#xff0c;之后就是次常用的元组、集合与字典了。 5.3. 元组和序列 元组和之前讲过的列表有很多共同特性&#xff0c;例如索引和切片操作。实际上&#xff0c;他们是 序列 数据类型&#xff08;list, tuple, range&#xff09;中的两种。 一个元组…

跟我一起学.NetCore之依赖注入

前言现阶段而言&#xff0c;依赖注入相关组件如果不会用一两个&#xff0c;感觉在Code的世界里肯定是落伍了&#xff0c;最起码得有工厂模式的思想&#xff0c;知道这样做的好处&#xff1b;提及到依赖注入&#xff0c;通常会关联出两个概念&#xff1a;Ioc(控制反转)和DI(依赖…

每天一小时python官方文档学习(六)————循环和条件控制的进阶用法

学习完数据结构之后&#xff0c;我们就能够对之前在第二天中讲过的流程控制工具&#xff0c;添加更多的用法了&#xff0c;这里主要介绍的是for循环语句和if与while条件判断语句。 5.6. 循环的技巧 我们学过的遍历序列for i in range() 、for i in list() 和 for i in tuple(…

跟我一起学.NetCore之依赖注入作用域和对象释放

前言上一小节简单阐述了依赖注入及Asp.NetCore中自带依赖注入组件的常规用法&#xff0c;其中提到容器管控了自己创建对象的生命周期&#xff0c;包含了三种生命周期&#xff1a;Singleton、Scoped、Transient&#xff0c; 对于Singleton、Transient相对于Scoped来说比较好理解…

leetcode738. 单调递增的数字

一:芭比Q了 又掉一个粉 啊呜呜呜呜呜 如果作为一个领导者来说&#xff0c;首先就是要以身作则&#xff0c;自己都做不到 &#xff0c;那就没什么威信去要求手下人按照要求去做 二:题目 三:上码 class Solution { public:int monotoneIncreasingDigits(int n) {/**思路:1.这…

每天一小时python官方文档学习(七)————模块与包

6. 模块 模块是一个包含Python定义和语句的文件&#xff0c;实际上就是一个正常的.py文件。但是作用和普通需要运行的程序不一样&#xff0c;它实际上有点像函数。如果说函数实现了代码的重用&#xff0c;模块则是实现了函数的重用。我们如果想在不同的程序中使用同一个函数&a…

大揭秘| 我司项目组Gitlab Flow DevOps流程

长话短说&#xff0c;本文全景呈现我司项目组gitlab flow && devopsGit Flow定义了一个项目发布的分支模型&#xff0c;为管理具有预定发布周期的大型项目提供了一个健壮的框架。DevOps 强调的是团队通过自动化的工具协作和高效地沟通来完成软件的生命周期管理&#xf…

leetcode714.买卖股票的

一:题目 二&#xff1a;上码 class Solution { public:int maxProfit(vector<int>& prices, int fee) {/**思路:*/int ans 0;int minPrice prices[0];//最低时买入for(int i 1; i < prices.size(); i) {//低价买入minPrice min(minPrice,prices[i]);if(price…

C++ 学习之旅(1)——编译器Compiler

简单来说&#xff0c;由C代码文件生成可执行文件的过程如下&#xff1a; #mermaid-svg-GQamCVEXMVkYEemz {font-family:"trebuchet ms",verdana,arial,sans-serif;font-size:16px;fill:#333;}#mermaid-svg-GQamCVEXMVkYEemz .error-icon{fill:#552222;}#mermaid-svg-…

掌握Rabbitmq几个重要概念,从一条消息说起

RabbitMQ 是功能强大的开源消息代理。根据官网称&#xff1a;也是使用量最广泛的消息队列。就像他的口号“Messaging that just works”&#xff0c;开箱即用使用简单&#xff0c;支持多种消息传输协议&#xff08;AMQP、STOMP、MQTT&#xff09;。一个应用程序或者服务如何使用…

122. 买卖股票的时机

一&#xff1a;题目 二&#xff1a;上码 class Solution { public:int maxProfit(vector<int>& prices) {/**思路:1.这里用的是贪心算法&#xff08;我们每隔两天计算一次赚的钱 只要大于0的话 那就是赚的&#xff09;2.我们手里最多只能有一只股票,所以我们可以当…

C++ 学习之旅(2)——链接器Linker

每一个.cpp文件经过编译之后都会生成对应的.obj文件&#xff0c;然后通过链接器把它们进行链接&#xff0c;最后就可以生成.exe可执行文件了。 举个例子&#xff0c;假设我们有一个 Math.cpp 文件和 Log.cpp 文件&#xff1a; Math.cpp #include <iostream>void Log(c…

使用 WPF 版简易 SIP 服务器向 GB28181 摄像头发送直播请求

使用 WPF 版简易 SIP 服务器向 GB28181 摄像头发送直播请求目录一、引言二、项目渊源三、软件使用及 SIP INVITE 流程(一) 注册和心跳(二) 直播 INVITE四、注意事项五、资源独立观察员 2020 年 9 月 16 日一、引言之前写过一篇博客《使用 GB28181.Solution ZLMediaKit MediaSe…

leetcode968. 监控二叉树

一:论语 这个有意思,我们可以从中得出的是&#xff0c;一个人过错 其实是潜意思决定的 行为见品质 但知错更改也是nice的 二:题目 三:上码 /*** Definition for a binary tree node.* struct TreeNode {* int val;* TreeNode *left;* TreeNode *right;* Tr…