定义一个函数
函数是可以重复执行的语句块,可以重复调用
用于封装语句块, 提高代码的重用性。
函数是面向过程编程的最小单位
def 语句
用来定义( 创建)函数
def 函数名(形式参数列表):
语句块
-
函数代码块以 def 关键词开头,后接函数标识符名称和圆括号 ()
-
函数名是一个变量,不要轻易对其赋值
-
函数有自己的名字空间,在函数外部不可以访问函数内部的变量,在函数内部可以访问函数外部的变量,但不能轻易对其改变
-
函数的形参列表如果不需要传入参数,形式参数列表可以为空
-
任何传入参数和自变量必须放在圆括号中间,圆括号之间可以用于定义参数。
-
函数内容以冒号 : 起始,并且缩进。
-
return [表达式] 结束函数,选择性地返回一个值给调用方,不带表达式的 return 相当于返回 None。
函数的调用
函数名(实际调用传递参数)
函数调用是一个表达式
如果函数内没有return 语句,函数执行完毕后返回 None 对象
return 语句
return [表达式]
ps:[] 代表 内部的内容可以省略
用于函数的内部,结束当前函数的执行,返回到调用此函数的地方,同时返回一个对象的引用关系
函数参数
-
函数的调用传参
-
位置传参 实际参数传递时,实参和形参按**位置**来依次对应
-
关键字传参 实际参数传递时,实参和形参 按**名称**依次对应
-
-
函数的形式参数定义方法
-
函数的缺省参数(默认参数)
-
def 函数名(形参名1=默认实参1, 形参名2=默认实参2, ... ): 语句块
-
缺省参数即默认实参,必须自右向左依次存在(即,如果一个参数有缺省参数,则其右侧的所有参数都必须有缺省参数)
-
-
形参的定义
-
位置形参
-
def 函数名(形参名1, 形参名2, ...): pass
-
-
星号元组形参(*args)
-
def 函数名(*元组形参名): pass
-
收集多余的位置实参 > 元组形参名一般命名为args
-
-
命名关键字形参
-
def 函数名(*, 命名关键字形参1, 命名关键字形参2, ...): pass # 或者 def 函数名(*args, 命名关键字形参1, 命名关键字形参2, ...): pass
-
强制,所有的参数都必须用关键字传参
-
-
双星号字典形参(**kwargs)
-
def 函数名(**kwargs): pass
-
收集多余的关键字传参 > 字典形参名最多有一个, > 字典形参名 一般命名为 kwargs
-
- 位置形参,星号元组形参,命名关键字参数,双星号字典形参,缺省参数可以混合使用。 - 函数的形参定义自左至右的顺序为:位置形参,星号元组形参,命名关键字参数,双星号字典形参
-
-
-
可变不可变
-
可更改(mutable)与不可更改(immutable)对象
-
在 python 中,strings, tuples, 和 numbers 是不可更改的对象,而 list,dict 等则是可以修改的对象。
-
-
不可变类型
-
- 数值型(整数,浮点数)
-
- 布尔值bool
-
- None 空值
-
- 字符串str
-
- 元组tuple
-
-
可变类型
-
- 列表 list
-
- 字典 dict
-
- 集合 set
-
-
-
-
返回值
-
函数可以使用`return`语句来返回一个或多个值。 如果没有明确的`return`语句,函数将默认返回`None`。
-
-
匿名函数
-
在Python中,匿名函数通常使用`lambda`关键字来创建。匿名函数也被称为lambda函数,它是一种简单的、一行的函数,常用于临时需要一个小函数的地方。
-
lambda [函数的参数列表]: 表达式
-
- 创建一个匿名函数对象 - `lambda`是关键字,表示你正在定义一个匿名函数。 - 同 def 类似,但不提供函数名 - `[函数的参数列表]`是函数的参数,可以有零个或多个参数,参数之间用逗号分隔。 - `: 表达式`是函数的返回值,通常是一个表达式,匿名函数会计算这个表达式并返回结果。 lambda 表达式 的创建函数只能包含一个表达式
-
-
变量作用域
-
什么是变量作用域
-
一个变量声明以后,在哪里能够被访问使用,就是这个变量"起作用"的区域:也就是这个变量的作用域
-
一般来说,变量的作用域,是在函数内部和外部的区域 来体现,因此常常与函数有关
-
-
局部变量和全局变量
-
局部变量
-
- 定义在函数内部的变量称为局部变量(函数的形参也是局部变量) - 函数内部的变量只能在函数内部或者函数内部的函数内部访问 ,函数外部不能访问 - 局部变量在函数调用时才能够被创建,在函数调用之后会自动销毁
-
-
全局变量
-
- 定义在函数外部,模块内部的变量称为全局变量 - 全局变量, 所有的函数都可以直接访问(取值,但函数内部不能直接将其赋值改变)
-
-
-
局部作用域修改全局变量
-
global 变量名1, 变量名2, ....
-
global
-
全局变量如果要在函数内部被赋值,则必须经过全局声明 global
-
默认全局变量在函数内部可以使用,但只能取值,不能赋值
-
不能先声明为局部变量,再用 global 声明为全局变量,此做法不符合语法规则
-
函数的形参已经是局部变量,不能用 global 声明为全局变量
-
-
-
告诉python 的解释执行器, global 语句声明的一个或多个变量, 这些变量是全局变量
-
-
局部作用域修改外部变量
-
前提:必须是函数嵌套
-
在函数内部 提前用nonlocal声明 函数内部的某个变量为外部的变量
-
变量的查找顺序还是遵从:LEGB顺序
-
nonlocal 语句
-
格式:nonlocal 变量名
-
将局部作用域中变量声明为外部函数嵌套作用域中的变量。
-
-
-
-
LEGB顺序
-
Local (L)
-
- 本地作用域,指当前函数内部的变量。
-
-
Enclosing (E)
-
闭包函数外的函数作用域,指嵌套函数的外部函数中定义的变量。
-
-
Global (G)
-
全局作用域,指模块级别定义的变量。
-
-
Built-in (B)
-
内建作用域,指 Python 预定义的变量、函数等,如 `len`、`sum` 等。
-
-
-
-
函数的内存分配
-
将函数的代码存储到代码区,函数体中的代码不执行。
-
调用函数时,在内存中开辟空间(栈帧),存储函数内部定义的变量。
-
函数调用后,栈帧立即被释放。
-
传参说明
-
不可变类型的数据传参时,函数内部不会改变原数据的值。
-
可变类型的数据传参时,函数内部可以改变原数据。
-
-
函数自调用(递归)
-
函数直接或间接的调用自身
-
- 递归一定要控制递归的层数,当符合某一条件时要终止递归调用
-
- 几乎所有的递归都能用while循环来代替
-
实现方法
-
先假设此函数已经实现
-
-
-
优点
-
递归可以把问题简单化,让思路更为清晰,代码更简洁
-
-
缺点
-
递归因系统环境影响大,当递归深度太大时,可能会得到不可预知的结果
-