Python学习10(函数)

函数是可重用的程序代码块。函数的作用可以实现代码的一致性。

目录

一、注意

二、文档字符串

三、return返回值

四、函数也是对象

五、变量定义域

全局变量︰

局部变量:

六、参数的传递

传递可变对象的引用

传递不可变对象的引用

七、浅拷贝和深拷贝

八、参数类型

位置参数

默认值参数

命名参数

可变参数

强制命名参数

九、lambda表达式和匿名函数

十、eval()函数 

十一、递归函数

十二、嵌套函数(内部函数)

十三、nonlocal和global

十四、LEGB规则


def 函数名([参数列表]):
    '''文档字符串'''
    函数体/若干语句

一、注意

Python执行def时,会创建一个函数对象,并绑定到函数名变量上。

(1)圆括号内是形式参数列表,有多个参数则使用逗号隔开

(2)形式参数不需要声明类型,也不需要指定函数返回值类型

(3)无参数,也必须保留空的圆括号

(4)实参列表必须与形参列表——对应

(1)内置函数对象会自动创建

2)标准库和第三方库函数,通过import导入模块时,会执行模块中的def语句

二、文档字符串

        程序的可读性最重要,一般建议在函数体开始的部分附上函数定义说明,这就是“文档字符串”,也有人成为“函数的注释”。我们通过三个单引号或者三个双引号来实现,中间可以加入多行文字进行说明。

三、return返回值

        1.如果函数体中包含return语句,则结束函数执行并返回值

        2.如果函数体中不包含return语句,则返回None值

        3.要返回多个返回值,使用列表、元组、字典、集合将多个值“存起来”即可

四、函数也是对象

        Python中,“一切都是对象”。实际上,执行def定义函数后,系统就创建了相应的函数对象。

def a(n):
    for i in range(n):
        print("I love you")
print(a)
a(2)
b=a
b(2)
'''
结果为:
<function a at 0x000001F167EAF040>
I love you
I love you
I love you
I love you

'''

五、变量定义域

        变量起作用的范围称为变量的作用域,不同作用域内同名变量之间互不影响。变量分为:全局变量、局部变量。

        可以运用locals()和globals()返回局部变量和全局变量的字典序列。

全局变量︰

        1.在函数和类定义之外声明的变量。作用域为定义的模块,从定义位置开始直到模块结束。

        2.全局变量降低了函数的通用性和可读性。应尽量避免全局变量的使用。

        3.全局变量一般做常量使用。

        4.函数内要改变全局变量的值,使用global声明一下

局部变量:

        1.在的数体中(包含形式参数)声明的变量。

        2.局部变量的引用比全局变量快,优先考虑使用。

        3.如果局部变量和全局变量同名,则在函数内隐藏全局变量,只使用同名的局部变量

六、参数的传递

        函数的参数传递本质上就是︰从实参到形参的赋值操作。Python中“一切皆对象”,所有的赋值操作都是“引用的赋值”。所以,Python中参数的传递都是“引用传递”,不是“值传递”。具体操作时分为两类︰

        1.对“可变对象”进行“写操作”,直接作用牛原对象本身。

        2.对“不可变对象”进行“写操作”,会产生一个新的“对象空间”,并用新的值填充这块空间。(起到其他语言的“值传递”效果,但不是“值传递”)

        可变对象有∶

        字典、列表、集合、自定义的对象等

        不可变对象有︰

        数字、字符串、元组、function等

传递可变对象的引用

        传递参数是可变对象(例如∶列表、字典、自定义的其他可变对象等),实际传递的还是对象的引用。在函数体中不创建新的对象拷贝,而是可以直接修改所传递的对象。

传递不可变对象的引用

        传递参数是不可变对象(例如: int、float、字符串、元组、布尔值),实际传递的还是对象的引用。在”赋值操作”时,由于不可变对象无法修改,系统会新创建一个对象。

七、浅拷贝和深拷贝

        为了更深入的了解参数传递的底层原理,我们需要讲解一下“浅拷贝和深拷贝”。我们可以使用内置函数: copy(浅拷贝)、deepcopy(深拷贝)。
        浅拷贝∶不拷贝子对象的内容,只是拷贝子对象的引用。
        深拷贝∶会连子对象的内存也全部拷贝一份,对子对象的修改不会影响源对象

        传递不可变对象是浅拷贝,传递参数是不可变对象(例口: int、 float、字符串、元组、布尔值),实际传递的还是对象的引用。但在’写操作’时,会创建一个新的对象拷贝。这个拷贝使用的是“浅拷贝”,不是“深拷贝”。

八、参数类型

位置参数

        函数调用时,实参默认按位置顺序传递,需要个数和形参匹配。

默认值参数

        我们可以为某些参数设置默认值,这样这些参数在传递时就是可选的。默认值参数放到位置参数后面。

命名参数

        我们也可以按照形参的名称传递参数,称为“命名参数”,也称“关键字参数”。

def f1(a,b,c):
    print(a,b,c)
f1(1,2,3)          #位置参数
f1(a=1,b=2,c=3)    #命名参数

可变参数

        可变参数指的是“可变数量的参数”。分两种情况︰

        1.*param (一个星号),将多个参数收集到一个“元组”对象中。

        2.**param(两个星号),将多个参数收集到一个“字典”对象中。

        (打包?)

强制命名参数

        在带星号的“可变参数”后面增加新的参数,必须在调用的时候“强制命名参数”。

def f1(*a,b,c):
    pass
f1(1,2,3,b=4,c=5)

九、lambda表达式和匿名函数

        lambda表达式可以用来声明匿名函数。lambda函数是一种简单的、在同一行中定义函数的方法。lambda函数实际生成了一个函数对象。
        lambda表达式只允许包含一个表达式,不能包含复杂语句,该表达式的计算结果就是函数的返回值。

lambda arg1,arg2,arg3... :<表达式>

        arg1/arg2/arg3为函数的参数。<表达式>相当于函数体。运算结果是:表达式的运算结果。

add=lambda a, b: a+b
#函数名称=lambda 传入参数:传出参数

十、eval()函数 

        执行一个字符串表达式,并返回表达式的值

        语法: eval(source[, globals[, locals]]) -> value

        参数:

        source :一个Python表达式或函数compile()返回的代码对象

        globals -- 变量作用域,全局命名空间,如果被提供,则必须是一个字典对象

        locals -- 变量作用域,局部命名空间,如果被提供,可以是任何映射对象

十一、递归函数

        递归函数指的是︰自己调用自己的函数,在函数体内部直接或间接的自己调用自己。

        每个递归函数必须包含两个部分︰

        1.终止条件

        表示递归什么时候结束。一般用于返回值,不再调用自己。

        2.递归步骤

        把第n步的值和第n-1步相关联。

        递归函数由于会创建大量的函数对象、过量的消耗内存和运算能力。在处理大量数据时,谨慎使用。

十二、嵌套函数(内部函数)

        在函数内部定义的函数

        一般在什么情况下使用嵌套函数?

        1.封装–数据隐藏外部无法访问“嵌套函数”。

        2.贯彻DRY(Don’ tRepeat Yourself)原则嵌套函数,可以让我们在函数内部避免重复代码。

        3.闭包

十三、nonlocal和global

        nonlocal
        用来声明外层的局部变量
        global
        用来声明全局变量

十四、LEGB规则

        Python在查找“名称“时,是按照LEGB 规则查找的︰Local-->Enclosed-->Global-->Built in

        Local指的就是函数或者类的方法内部

        Enclosed指的是嵌套函数(一个函数包裹另一个函数,闭包)

        Global指的是模块中的全局变量

        Built in指的是 Python为自己保留的特殊名称

        如果某个name映射在局部(local)命名空间中没有找到,接下来就会在闭包作用域(enclosed)进行搜索,如果闭包作用域也没有找到,Python就会到全局(global)命名空间中进行查找,最后会在内建(built-in)命名空间搜索(如果一个名称在所有命名空间中都没有找到,就会产生一个(NameError ) 

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值