函数的动态参数和命名空间还有关键字/嵌套

1,动态参数(形参):顾名思义就是这个参数是时刻在变化的,动态格式:   *函数名  =动态参数,列如:(*food)

  • 1>位置参数的动态参数:*args()能接收任意的位置参数.

 

def func(*args):  # *args接收所有的位置参数
    print("我喜欢:", args)  # 我喜欢: ('李智恩', '陈乔恩', '宋慧乔', '吴宣仪')
    # 此时返回的是一个元组


func("李智恩", "陈乔恩", "宋慧乔", "吴宣仪")


def func(*args, a, b):
    print("我喜欢:", args, a, b)
    # TypeError: func() missing 2 required keyword-only arguments: 'a' and 'b'
    # 会 包这样一个错,是因为这是的位置参数都被动态参数接收,
    # 等到位置参数a,b的时候即郿参数了,函数调用不起来,程序运行失败


func("李智恩", "陈乔恩", "宋慧乔", "吴宣仪")
# 动态参数接收数据时那必须放在位置参数的后边
  • 默认参数:

 

def func(a, b, c="李子璇", *args):
    print("我喜欢:", a, b, c, args)


func("李智恩", "陈乔恩", "宋慧乔", "吴宣仪")  # # 我喜欢:"李智恩","陈乔恩","宋慧乔",("吴宣仪,")
func("李智恩", "陈乔恩")  # 我喜欢:"李智恩","陈乔恩","李子璇"()...空的元组,因为没有值给它
func("李智恩", "陈乔恩", "宋慧乔")  # 喜欢:"李智恩","陈乔恩","宋慧乔"().....空的元组,同样没有值给它
func("李智恩", "陈乔恩", "宋慧乔", "吴宣仪", "赵丽颖")  # 我喜欢:"李智恩","陈乔恩","宋慧乔",("吴宣仪","赵丽颖")
  • #由此可见:当默认参数在动态参数前边时,只有一种情况默认值才会产生.
  • #....当位置参数>动态参数*>默认参数时,默认值参数始终生效(当给默认值参数关键字参数时,默认参数失效)

2,动态接收关键字参数,用**来接收动态关键字参数.

  • 2.1>列如:

 

def func(**kwargs):
    print(kwargs)
func(a=1, b=2, c=3)  # {"a":1,"b":2,"c":3}返回的是一个字典
  • 2.2>列如:

 

def func(a, b, **kwargs):
    print(a, b, kwargs)

func(1,2,c=3)  # 1 2 {'c': 3}返回的是一个字典和2个元素
func(1, b=2, 3)  # 报错,关键字和位置参数混乱
# SyntaxError: positional argument follows keyword argument
func(a=1, b=2, c=3)  # 1 2 {'c': 3}  # 返回的是一个字典和2个元素
  • #顺序是:位置参数>*args>默认值参数>**kwargs
  • #*args接收任意的动态位置参数
  • #**kwargs接收的是动态关键字参数
  • 2.3>list和dict和字符串的传参:调用函数的时候func(*list/*dict/*s(s="帅爆太阳的男人"))...................把相应的list/dict/字符串拍碎放到元组里

 

def func(*args):
    print(args)


lst = ["","","","","","",""]
dic = {1: "", 2: "", 3: "", 4: "", 5: "", 6: "", 7: ""}
s = "帅爆太阳的男人"
func(*lst)  # ('帅', '爆', '太', '阳', '的', '男', '人')
# 把lst拍碎放到一个新的元组中,实质是把lst中的每一个元素迭代放到元组中
func(*dic)  # (1, 2, 3, 4, 5, 6, 7)
# 把dic拍碎放到一个新的元组中,实质是把dic中的每一个元素key迭代放到元组中,字典拍碎只有key值
func(*s)  # ('帅', '爆', '太', '阳', '的', '男', '人')
# 把s字符串拍碎放到一个新的元组中,实质是把字符串中的每一个元素迭代放到元组中
func(*lst, *dic)  # ('帅', '爆', '太', '阳', '的', '男', '人', 1, 2, 3, 4, 5, 6, 7)
# 把lst中每一个元素和dic中的key值作为元素放到元组中
  • 补充:当dic中拍碎就用(**dic)拍出来的是键值对.

3,命名空间:在我们定义函数和值之间的关系时,会开辟一个内存空间,这个空间就叫做命名空间.

  • 命名空间的分类:
    • 1>全局命名空间-->我们在.py文件中函数外声明的变量都属于全局命名空间--->python中我们自己的定义函数
    • 2>局部命名空间-->在函数中声明的变量就放在局部你命名空间--->python中我们自己的定义函数
    • 3>内置函数空间-->是python解释器中已有的函数命名--->python的内置函数
  • 加载顺序:内置函数空间-->全局命名空间--->局部命名空间(函数调用的时候)
  • 取值顺序:局部命名空间-->全局命名空间-->内置命名空间
  • 3.1>作用域:顾名思义以就是作用的区域(范围),因此分为全局作用域和局部作用域
    • 全局作用域包括:全局命名空间 + 内置函数空间
    • 局部作用域包括:局部命名空间 

用globals()来打印全局作用域的内容,locals()是用来查看局部作用域中的内容(变量和值之间的关系)

 

def func():
    a =40
    b = 20
    def abc():
        print("哈哈")
    print(a, b)  # 这里使用的是局部作用域  40 20
    print(globals())  # 打印全局作用域的内容,
    # {'__name__': '__main__', '__doc__': None, '__package__': None, 
    # '__loader__': <_frozen_importlib_external.SourceFileLoader object at 0x000001B5D9DF1FD0>, 
    # '__spec__': None, '__annotations__': {}, '__builtins__': <module 'builtins' (built-in)>,
    #  '__file__': 'D:/python_学习文件/python学习之路/帅爆太阳的男人/日记/blog_code/blog_demo.py', '__cached__': None, 
    # 'func': <function func at 0x000001B5D9CF3158>}
    print(locals())  # 打印的是局部作用域的内容
    # {'abc': <function func.<locals>.abc at 0x000001B5DA0626A8>, 'b': 20, 'a': 40}

func()

4,函数的嵌套:调用函数的时候必须用()如果不写那就不调用,在嵌套中最重要的是看调用时那个函数并此时打印的是那个值。

 

def func1():  #这个是2个并列的函数,执行顺序就按照函数对奥用的顺序和执行顺序
    print(111)
def func2():
    print(222)
    func1()
func2()
print(333)
# 222
# 111
# 333 

 

def func2():
    print(222)
    def func3():
        print(666)
    print(444)
    func3()
    print(888)
print(333)
func2()
print(555)
# 333
# 222
# 444
# 666
# 888
# 555
  • 分析:当遇到函数的嵌套时,先看母函数(最外边那一层)定义函数名可以先跳过值接从上到下先找(print)或者调用函数()遇到那个就执行那个就好了,当遇到调用的函数内部有子函数时也是***层层降维,从上到下***.

5,关键字global和nonlocal

  5.1>global在局部变量中调用全局定义好的变量来重新赋值.

 

a = 100
def func():
    global a  # 加了global表示不在局部创建这个变量而是直接使用全局的a
    # 并同时把局部值从新赋值给全局变量中拿过来的变量(全局变量和局部变量必须一致,不然拿不过来)
    # 此时的局部变量是局部变量赋的值
    a = 28
    print(a)
func()
print(a)
# 28
# 28
  • 5.2>nonlocal表示在局部作用中,调用非本局部中的变量,也不调用全局中的变量.(调用里它最近的一个相同名称的变量)还是"层层降维,从上到下"
a = 10
def func1():
    a = 20
    def func2():
        nonlocal a
    a = 30
    print(a)
    func2()
    print(a)
func1()
# 30
# 30
posted @ 2018-07-15 17:10  帅爆太阳的男人  阅读(155)  评论(0)    收藏  举报