day10
1. 函数参数-动态传参(形参)
1. 动态接收位置参数 # *args(arguments) # * 在这里表示接收位置参数的动态传参, 接收到的是元组. def chi(*food): print("我要吃", food) chi("⼤⽶饭", "⼩⽶饭") # 我要吃 (大米饭,小米饭) # 顺序: 位置参数 => *args(arguments) => 默认值参数 def chi(name, *food, location="北京"): # 参数名数food, *表示动态传参 print(name,"要在"+location+"要吃",food) chi("闫康琪","狗不理","大麻花") # 闫康琪 要在北京要吃 ('狗不理', '大麻花') chi("闫康琪","馒头") # 闫康琪 要在北京要吃 ('馒头',) 2. 动态接收关键字参数 # **kwargs # ** 在这里表示接收关键字参数的动态传参, 接收到的是字典. def func(**kwargs): print(kwargs) func(a=1, b=2, c=3) # {'a': 1, 'b': 2, 'c': 3} func(a=1, b=2) # {'a': 1, 'b': 2} # 顺序: 位置参数 => *args(返回的是元组) => 默认值参数 => **kwargs(返 回的是字典) # 以上参数可以随意搭配使用,但是顺序不能变 def fun(a, *args, c="哈哈", **kargs): print(a,args,c,kargs) fun(1, 2, 3, d=5) 3. 接收所有参数 def func(*args, **kwargs): # 无敌 *args相当于一个聚合的作用 print(args, kwargs) func(1,2,3,4,5,a=6,b=7,c=8)
2. 动态参数的另一种传参和函数的注释
1. 聚合和打散 # 形参: 聚合 def func(*food): # 聚合, 动态的位置参数 print(food) lst = ["鸡蛋","煎饼果子","猪蹄","滋滋冒油"] # 实参: 打散 func(*lst) # 打散, 把list, tuple, set, str 进行迭代打散 2. 利用聚合和打散来传参 # 在实参位置上给⼀个序列,列表,可迭代对象前⾯加个*表⽰把这个序列按顺序打散成单个参数. # 在形参的位置上的* 表⽰把接收到的参数组合成⼀个元组. def fun(*args): # 聚合成元组 print(args) lst = [1, 4, 7] fun(lst[0], lst[1], lst[2]) fun(*lst) # 将列表打散成单个元素 s = "⾂妾做不到" fun(*s) # 字符串也可以打散, (可迭代对象) # 在实参位置上给⼀个字典,字典前⾯加个** 表⽰把这个序列按顺序打散成关键字. # 在形参的位置上的** 表⽰把接收到的参数组合成⼀个字典. def fun(**kwargs): # 聚合成字典 print(kwargs) dic = {'a':1, 'b':2} fun(**dic) # 打散成关键字参数 3. 函数的注释 def func(a, b): """ 这个函数是用来计算a和b的和 :param a: 第一个数据 :param b: 第二个数据 :return: 返回的是两个数的和 """ return a + b print(func.__doc__) # document文档
3. 命名空间和作用域
1.命名空间 命名空间分类 (1) 内置名称空间: python解释器内部运行时的变量函数 (2) 全局名称空间: 我们在py文件中,函数外声明出来的变量,函数 (3) 局部名称空间: 在函数内部声明的变量和函数 加载顺序: (1) 内置命名空间 (2) 全局命名空间 (3) 局部命名空间(函数被执⾏的时候) 取值顺序: (1) 局部命名空间 (2) 全局命名空间 (3) 内置命名空间 a = 10 # 全局名称空间中的内容 def fn(): # fn也在全局名称空间中 b = 20 # 局部名称空间 print(a) # 局部空间 def gn(): # gn在全局空间中 print(a) fn() # 全局空间 gn() # 全局空间
2. 作用域 作⽤域就是作⽤范围, 按照⽣效范围来看分为 全局作⽤域和局部作⽤域. 作用域: (1) 全局作用域: 内置命名空间 + 全部命名空间 (2) 局部作用域: 局部命名空间(函数被调用) 3. globals()和locals() globals()函数来查看 全局作⽤域 中的内容 locals()来查看 当前作⽤域 中的变量和函数信息 a = 10 def func(): a = 40 b = 20 def abc(): print("哈哈") print(a, b) # 这⾥使⽤的是局部作⽤域 print(globals()) # 打印全局作⽤域中的内容 print(locals()) # 打印局部作⽤域中的内容 func()
4. 函数的嵌套
# 只要遇⻅了()就是函数的调⽤. 如果没有()就不是函数的调⽤ # 函数的执⾏顺序 # 1. def outer(): print("哈哈") def inner(): print("呵呵") inner() outer() # 2. def outer(): print("哈哈") def inner_1(): print("呵呵") def inner_1_1(): print("嘻嘻") inner_1_1() print("吼吼") def inner_2(): print("嘿嘿") inner_2() inner_1() outer()
5. 关键字global和nonlocal
# golobal: 1.可以把全局中的内容引到函数的内部, 2.在全局创建一个变量 # 1.把全局变量拿到局部来用 a = 10 # 全局变量本身就是不安全的, 不能随意修改, 闭包 def func(): global a # 把全局变量a引到局部 a = 30 # 把全局中的a重新赋值成30 print(a) # 30 func() print(a) # 30 # 2.在全局创建一个变量 def func(): global a a = 3 func() print(a) # 3 # nonlocal: 寻找外层函数离他最近的变量 def outer(): a = 10 def inner(): # 我想在inner中改变最近一层a的值 nonlocal a # 找外层函数中离他最近的变量引入进来操作,不会找全局变量. a = 20 # 赋值,修改 print(a) # 20 inner() print(a) # 20 被nonlocal引过去修改成了20 outer() 练习: # 写出下面嵌套函数的答案 a = 1 def fun_1(): a = 2 def fun_2(): nonlocal a a = 3 def fun_3(): a = 4 print(a) print(a) fun_3() print(a) print(a) fun_2() print(a) print(a) fun_1() print(a)