python 函数嵌套的参数_Python day13:函数参数+函数对象+函数嵌套+名称空间+作用域...

一:可变长参数

可变长指的是参数的个数不固定

站在实参的角度,实参是用来为形参赋值的,如果实参的个数不固定,那么必须要有对应的形参能够接收溢出实参

*与*在形参与实参中的应用

在形参中用*与*

1.1 在形参名前加 *:* 会把溢出的位置实参存成元组,然后赋值其后的形参名

def func(x,*y): # y=(2,3,4)

print(x)

print(y)

func(1,2,3,4)

func(1)

func() # 位置形参x必须被传值

'''示范:'''

def add(*nums):

res = 0

for num in nums:

res += num

return res

res=add(1, 2, 3)

print(res)

1.2 在形参名前加**:**会把溢出的关键字实参存成字典,然后赋值其后的形参名

def func(x, **y): # y=(2,3,4)

print(x)

print(y)

func(1,a=111,b=222,c=333)

func(a=111, b=222, x=1, c=333)

在实参中用\*与\**

def func(x, y, z):

print(x, y, z)

1.3 在实参前加*:*会把其后的值打散成位置实参

nums = [1, 2, 3]

func(*nums) # func(1,2,3)

# 若只有一个形参,则多余出来的值没处放,会出错

def fun(x)

print(x)

1.4 在实参前加 **:**会把其后的值打散关键字实参

dic = {'y': 111, 'z': 222, 'x': 333}

func(**dic) # func(y=111,z=222,x=333)

'''

在形参与实参中混用*与**

'''

'''

同时使用*与**的作用是可以把外部传的值原封不动的传给另一个函数,这在闭包函数,装饰器中有很大作用

'''

def index(x,y,z,a,b,c):

print("index===>",x,y,z,a,b,c)

def wrapper(*args, **kwargs): # args=(1, 2, 3,) kwargs={"a":111,"b":222,"c":333}

index(*args, **kwargs) # index(*(1, 2, 3,),**{"a":111,"b":222,"c":333})

# index(1,2,3,c=333,b=222,a=111)

wrapper(1, 2, 3, a=111, b=222, c=333)

函数参数总结:

# def func(x,y=222,*args,**kwargs):

# pass

# 命名关键字形参(了解即可)

def func(x, y=222, *args, n=777,m, **kwargs): # m,n必须按照关键字实参的格式为其赋值

print(x) # 1

print(y) # 2

print(args) # (3,4,5)

print("m===>", m)

print("n===>", n)

print(kwargs)

func(1, 2, 3, 4, 5, n=88888,m=6666666, a=11, b=22, c=33)

二、函数对象

函数对象指的是函数可以被当成变量去使用

def foo(): # foo = 函数的内存地址

print('from foo')

1 可以被赋值

f = foo

print(f is foo)

f()

2 可以当作参数传给一个函数

def bar(func):

print(func)

func()

bar(foo)

3 可以当成一个函数的返回值

def bar(func):

return func

res=bar(foo)

print(res)

4 可以当成容器类型的元素

l = [foo]

print(l)

l[0]()

示例:当我们的主函数是由多个其他函数组成,即我们需要使用许多的if来判断用户输入且调用对应的函数时候,可以使用这种容器的方法,使得代码量减少,同时,在面试时,若被问到如何减少if操作时,可使用字典替换

def login():

print('登录功能......')

def withdraw():

print('提现功能......')

def transfer():

print('转账功能......')

def recharge():

print('充值功能')

func_dic={

"1": [login,"登录"],

"2": [withdraw,"提现"],

"3": [transfer,"转账"],

"4": [recharge,"充值"]

}

func_dic["1"][0]()

while True:

print("0 退出")

for k in func_dic:

print("%s %s" %(k,func_dic[k][1]))

choice = input("请输入你的指令编号: ").strip()

if choice == "0":

break

if choice in func_dic:

func_dic[choice][0]()

else:

print('输入的指令不存在')

三、函数嵌套

1 函数的嵌套调用

def bar():

print('from bar')

def foo():

print('from foo')

bar()

foo()

案例:

def max2(x,y):

if x > y:

return x

else:

return y

def max4(a,b,c,d):

res1 = max2(a,b)

res2 = max2(res1,c)

res3 = max2(res2,d)

print(res3)

max4(1,2,3,4)

2 函数的嵌套定义

def f1():

print('from f1')

# f2 = 函数的内存地址

def f2():

print("from f2")

f1()

定义在函数内的函数特点是: 正常情况只能在函数体内调用

from math import pi

def circle(radius,mode=0):

def perimiter(radius):

return 2 * pi * radius

def area(radius):

return pi * (radius ** 2)

if mode == 0:

return perimiter(radius)

elif mode == 1:

return area(radius)

res1=circle(3,0)

res2=circle(3,1)

print(res1)

print(res2)

-------------------------

18.84955592153876

28.274333882308138

def func():

x = 10

print(x)

def f2():

print('from f2')

f2()

func()

print(x)

---------------------------------

Traceback (most recent call last):

File "xxx", line 122, in

print(x)

NameError: name 'x' is not defined

10

from f2

四、名称空间与作用域

'''

名称空间:就是存放名字的地方

名(函数名、变量名等):存放在内存里

值(变量值等):存放在内存里

通过划分出各个名字空间,允许在不同的空间内,可以有相同的名字

1、内置名称空间:存放内置的名字(python解释器启动时便定义好的)如 print、input、len

生命周期:解释器启动则产生,解释器关闭则销毁 (python解释器在pyhton程序执行时运行,执行结束时结束)

2、全局名称空间:存放的是顶级的名字

生命周期:python程序运行时则产生,python程序结束则销毁

3、局部名称空间:函数内的名字

只有调用函数时,局部名字才产生,定义函数时,并不会产生,因为代码并未执行

生命周期:调用函数时产生,函数调用结束则销毁

访问 同名名字的优先级:局部>全局>内置

从当前位置往外查找

名字的查找优先级:

从当前位置往外查找,如果当前是在局部:局部名称空间->全局名称空间->内置名称空间

从当前位置往外查找,如果当前是在全局:全局名称空间->内置名称空间

'''

1 内置名称空间: 存放的是内置的名字,如print\input\len

生命周期: 解释器启动则产生,解释器关闭则销毁

2 全局名称空间: 存放的是顶级的名字

生命周期: python程序运行时则产生,python程序结束则销毁

x = 10

def func():

x = 111

print(x)

if 1:

y = 6666

3 局部名称空间:函数内的名字

生命周期: 调用函数时则产生,函数调用结束则销毁

名字的查找优先级:

从当前位置往外查找,如果当前是在局部:局部名称空间->全局名称空间->内置名称空间

从当前位置往外查找,如果当前是在全局:全局名称空间->内置名称空间

示范1:

def func():

len = 222

# print(len)

# len = 111

func()

print(len)

名称空间可以理解为一层套一层的关系,问题是嵌套关系是在函数定义阶段生成的,还是在函数调用阶段生成的?

x = 111

def foo():

print(x)

def bar(f):

x=222

f()

bar(foo)

一个非常重要的结论:名称空间的嵌套关系是函数定义阶段(即扫描语法时)就固定死的,与函数的调用位置无关

x = 111

def func():

print(x)

x=2222

func()

练习

x=0

def f1():

# x=1

def f2():

# x=2

print(x)

f2()

f1()

len = 111

def f1():

len=2222

def f2():

len=3333

f1()

f2()

全局范围/全局作用域:内置名称空间+全局名称空间

特点:全局存活,全局有效

局部范围/局部作用域:局部名称空间

特点:临时存活,局部有效

了解:

global(****) 在局部名称空间中指定某个变量为全局变量

nonlocal(***)

案例1

x = 10

def func(x): # x = 值10的内存地址

# x = 值10的内存地址

x = 20

func(x) # func(值10的内存地址)

print(x)

案例2

x = [11,22,33]

def func(x): # x = 列表[11,22,33]的内存地址

# x = 列表[11,22,33]的内存地址

# x=444444444444

x[0] = 66666

func(x) # func(列表[11,22,33]的内存地址)

print(x)

案例3

x = [11,22,33]

def func():

x[0] = 66666

func()

print(x)

案例4

x = 10

def func():

global x

x=22

func()

print(x)

案例5:nonlocal生命名字是来自于外层函数的(了解)

x = 10

def f1():

x=111

def f2():

nonlocal x

x=222

f2()

print(x)

f1()

print(x)

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值