写点什么

跟着官方文档学 Python 之:函数

作者:甜甜的白桃
  • 2022 年 7 月 13 日
  • 本文字数:2054 字

    阅读完需:约 7 分钟

跟着官方文档学 Python 之:函数

Python 同其他的高级语言一样支持函数,不但可以灵活地定义函数,又内置了非常多好用的函数,可以直接调用,将代码变得更高级和抽象。

一、调用函数


Python 解释器内置了很多函数和类型,任何时候都能使用。详情可参考 Python 官网-内置函数说明 。另外,我们也可以在交互式命令行中,输入 help(内置函数名) 查看该函数的帮助信息。




Python 内置的函数中,还存在数据类型转换函数,例如 int() 将其他数据类型转换为整数。我们也可以将函数名赋值给一个变量,给函数起别名。



二、定义函数

1、基本方法


定义函数使用 def 语句,后面拼接函数名、参数和冒号:,返回值用 return 。如果没有 return 语句,函数执行结束后也会返回结果 None,return None 可简写成 return 。


在语法上,返回一个 tuple 可以省略括号,而多个变量可以同时接收一个 tuple,按位置赋给对应的值。所以,Python 的函数返回多值其实就是返回一个 tuple,例如 return n1,n2,n3 写起来更方便。


def my_abs(x):    if x >= 0:        return x    else:        return -x
复制代码


2、空函数


当还未想好怎么写函数的代码,可以先定义一个空函数(放一个 pass 语句),让代码能运行起来。


def nop():    pass  # pass 还可以用在其他语句里(缺少了 pass 代码运行会有语法错误)if age >= 18:    pass
复制代码

3、参数检查


给函数传入不恰当的参数时,内置函数会检查参数错误(抛出 TypeError),但我们定义的函数没有参数检查,所以我们要养成给函数做参数检查的习惯,不断完善函数。其中,数据类型检查可以用内置函数 isinstance() 实现。


def my_abs(x):    # 数据检查    if not isinstance(x,(int,float)):        raise  TypeError('错误参数类型')
if x >= 0: return x else: return -x
print('取绝对值' ,my_abs('123'))
复制代码


三、函数的参数


*args 是可变参数,args 接收的是一个 tuple

可变参数既可以直接传入:func(1, 2, 3),又可以先组装 list 或 tuple,再通过 *args 传入:func(*(1, 2, 3));


**kw 是关键字参数,kw 接收的是一个 dict

关键字参数既可以直接传入:func(a=1, b=2),又可以先组装 dict,再通过 **kw 传入:func(**{'a': 1, 'b': 2})。


使用 *args 和 **kw 是 Python 的习惯写法,也可以用其他参数名,但最好使用习惯用法。


# 1、位置参数# 将传入的多个值按照位置顺序依次赋给每个参数def test_01(x,n):   	return x + n  
# 2、默认参数# 可以简化函数的调用,例如 test_02(2) 相当于调用 test_02(2,2)'''1、通常将变化最大的参数-必选参数在前,变化最小的参数-默认参数在后2、可以按顺序提供默认参数,也可以不按顺序提供部分默认参数3、默认参数必须指向不变对象!比如用 L=None 替换 L=[],减少由于修改数据导致的错误,多任务环境下同时读取对象不需要加锁,同时读一点问题都没有'''def test_02(x,n=2): return x + n
# 3、可变参数# 允许传入 0 个或任意个参数,和定义一个 list 或 tuple 参数相比,仅仅在参数前面加了一个 * 号nums = [1, 2, 3]test_03(*nums)# *nums 表示把 nums 这个 list 的所有元素作为可变参数传进去
# 4、关键字参数# 允许传入 0 个或任意个含参数名的参数,这些关键字参数在函数内部自动组装为一个 dictdef person(name, age, **kw): print('name:', name, 'age:', age, 'other:', kw)
'''**extra 表示把 extra 这个 dict 的所有 key-value 用关键字参数传入到函数的 **kw 参数kw 将获得一个 dict,注意 kw 获得的 dict 是 extra 的一份拷贝,对 kw 的改动不会影响到函数外的 extra'''extra = {'city': 'Beijing', 'job': 'Engineer'}person('Jack', 24, **extra)
# 5、参数组合# 参数定义的顺序必须是:必选参数、默认参数、可变参数、命名关键字参数和关键字参数,不要同时使用太多的组合,否则函数接口的可理解性很差def f1(a, b, c=0, *args, **kw): print('a =', a, 'b =', b, 'c =', c, 'args =', args, 'kw =', kw)def f2(a, b, c=0, *, d, **kw): print('a =', a, 'b =', b, 'c =', c, 'd =', d, 'kw =', kw)f1(1, 2, 3, 'a', 'b', x=99) # 会输出 a = 1 b = 2 c = 3 args = ('a', 'b') kw = {'x': 99}f2(1, 2, d=99, ext=None) # 会输出 a = 1 b =2 c = 0 d = 99 kw = {'ext': None}# 通过一个 tuple 和 dict,也可以调用上述函数args = (1, 2, 3, 4)kw = {'d': 99, 'x': '#'}f1(*args, **kw) # 会输出 a = 1 b = 2 c = 3 args = (4,) kw = {'d': 99, 'x': '#'}args = (1, 2, 3)kw = {'d': 88, 'x': '#'}f2(*args, **kw) # 会输出 a = 1 b = 2 c = 3 d = 88 kw = {'x': '#'}# 故,对于任意函数,都可以通过类似 func(*args, **kw) 的形式调用它,无论它的参数是如何定义的
复制代码

四、递归函数


是指函数在内部调用函数本身,优点是定义简单、逻辑清晰,缺点是过深的调用会导致栈溢出。Python 标准的解释器未对尾递归做优化,几乎任何递归函数都存在栈溢出的问题。


👉如果在阅读过程中有任何疑问,欢迎在评论区留言参与讨论!

发布于: 刚刚阅读数: 3
用户头像

👩‍🦰 深耕测试开发 2021.02.23 加入

⭐ 坚信做好每个当下,美好一定会不期而遇! 2018年至今 坐标大连,负责移动端SDK开发 2015年 入职腾讯,负责手机QQ iOS开发 软件评测师认证 高中和中职信息技术教师资格证

评论

发布
暂无评论
跟着官方文档学 Python 之:函数_Python_甜甜的白桃_InfoQ写作社区