Python基础教程:形参 命名空间

一、形式参数

1.万能参数

有下列函数:

def eat(a, b, c, d):
    print('我请你吃%s、%s、%s、%s' %(a, b, c, d))
eat('烧花鸭','烧雏鸡','烧子鹅','蒸鹿尾')

我们在需要扩展时,会出现需要修改函数参数的问题,可以这样修改该函数:

def eat(a, b, c, d, e, f):
    print('我请你吃%s、%s、%s、%s' %(a, b, c, d, e, f))
eat('烧花鸭', '烧雏鸡', '烧子鹅', '蒸鹿尾', '蒸熊掌', '蒸羊羔')

我们可以意识到,面对类似问题,我们需要一种形参,可以接受所有的实参,万能参数应运而生。

  • *args

args 是约定俗成的名字,是 arguments 的简写,理论上可以使用 * + 任意字符 来表示,但一般不修改名称。它将所有位置参数聚合成一个元组,赋值给 args。

# 函数定义时,*代表聚合,他将所有位置参数聚合成一个元组,赋值给了args
def eat(*args):
    print('我请你吃%s、%s、%s、%s' % args)
eat('烧花鸭','烧雏鸡','烧子鹅','蒸鹿尾')
# 练习题:写一个函数:计算传入的所有数字之和
def sum(*args):
    s = 0
    for value in args:
        s += value
    return s
  • **kwargs

*args也是约定俗成的名字,是 key words arguments 的简写,接受关键字参数并将其转换成字典赋值给 kwargs 。

'''
遇到问题没人解答?小编创建了一个Python学习交流QQ群:778463939
寻找有志同道合的小伙伴,互帮互助,群里还有不错的视频学习教程和PDF电子书!
'''
def func(**kwargs):
    print(kwargs)
func(name='alex', age=18)
  • 万能参数的位置
# *args:放在位置参数的后面,默认值参数的前面
def func(a,b,*args,sex='男'):
    print(a,b)
    print(args)
    print(sex)
func(2,123,4,2,5,sex='女')
# **kwargs:放在所有参数最后
def func(a,b,*args,sex='男',**kwargs):
    print(a,b)
    print(args)
    print(sex)
    print(kwargs)
func(2,123,4,2,5,sex='女',name='alex',age=80)

2.仅限关键字参数(了解)

'''
遇到问题没人解答?小编创建了一个Python学习交流QQ群:778463939
寻找有志同道合的小伙伴,互帮互助,群里还有不错的视频学习教程和PDF电子书!
'''
# 下面函数的 c 只能用关键字赋值,且必须赋值
def func(a,b,*args,sex='男',c,**kwargs):
    print(a,b)
    print(args)
    print(sex)
    print(c)
    print(kwargs)
func(2, 123, 4, 2, 5,sex='女',name='alex',age=80,c='555')

3.形式参数的顺序

位置参数 -> *args -> 默认参数 -> 仅限关键字参数 -> **kwargs

4.***的用法

-* 在函数的调用时,代表打散

# *在函数的调用时,代表打散
def func(*args, **kwargs):
    print(args)             # (1, 2, 3, 22, 33)
    print(kwargs)
func(*[1, 2, 3],*[22, 33])                      # func(1, 2, 3, 22, 33)
func(*'da',*'12')                               # func('d', 'a', '1', '2')
# **在函数的调用时,也代表打散
def func(*args, **kwargs):
    print(args)             
    print(kwargs)
func({'name': '太白'}, {'age': 18})             # 字典传入args
func(**{'name': '太白'}, **{'age': 18})         # func(name='太白', age=18) 字典传入kwargs

三、命名空间(名称空间)

1. 命名空间

  • 全局命名空间

全局命名空间存储了每个变量与值的关系,只会记录函数的名称和内存地址,不会实际执行函数代码,只有在调用函数时才会执行。

'''
遇到问题没人解答?小编创建了一个Python学习交流QQ群:778463939
寻找有志同道合的小伙伴,互帮互助,群里还有不错的视频学习教程和PDF电子书!
'''
a = 1           # 开辟全局命名空间(整个 py 文件的命名空间)
b = 2
def func():
    pass
c = 3
  • 局部命名空间

调用函数会临死开辟局部(临时)命名空间(函数内部的命名空间),函数结束局部命名空间会随之消失。

a = 1           # 开辟全局命名空间(整个 py 文件的命名空间)
b = 2
def func():
    f = 5
    print(f)
c = 3
func()         
  • 内置命名空间

Python 源码提供的一些内置的函数,如print、input等等。

2. 作用域

  • 全局作用域:内置名称空间、全部名称空间

  • 局部作用域:局部名称空间

  • 不同作用域之间的关系

# 局部作用域可以引用全局作用据的变量,全部作用域不能引用局部作用域
# 局部作用域不能修改全局作用域的变量
date = 'Friday'
def func():
    date = 666                          # 这是在局部作用域新建一个同名变量,并没有修改全部作用域的变量
    print(date)
print(date)                             # result: Friday
func()                                  # result: 666

3. 取值顺序

局部命名空间 -> 全局命名空间 -> 内置命名空间(按照LEGB原则)

# LEGB即为:
# Locals
# Enclosing function
# Globals
# Builtins

4. 加载顺序

内置命名空间 -> 全局命名空间 -> 局部命名空间

四、高阶函数

例1:

'''
遇到问题没人解答?小编创建了一个Python学习交流QQ群:778463939
寻找有志同道合的小伙伴,互帮互助,群里还有不错的视频学习教程和PDF电子书!
'''
def func1():
    print('in func1')
    print(3)

def func2():
    print('in func2')
    print(4)

func1()
print(1)
func2()
print(2)

# result:
# in func1
# 3
# 1
# in func2
# 4
# 2

例2:

def func1():
    print('in func1')
    print(3)

def func2():
    print('in func2')
    func1()
    print(4)

print(1)
func2()
print(2)

# result:
# 1
# in func2
# in func1
# 3
# 4
# 2

例3:

'''
遇到问题没人解答?小编创建了一个Python学习交流QQ群:778463939
寻找有志同道合的小伙伴,互帮互助,群里还有不错的视频学习教程和PDF电子书!
'''
def fun2():
    print(2)

    def fun3():
        print(6)

    print(4)
    fun3()
    print(8)


print(3)
fun2()
print(5)

# result:
# 3
# 2
# 4
# 6
# 8
# 5

五、内置函数

"""本文件主要研究内置函数 globals 和 locals"""
a = 1
b = 2

def func():
    name = 'alex'
    age = 73
    print(locals())  # 返回的是字典,字典里面的键值对是当前作用域的所有内容

print(globals())  # 返回的是字典,字典里面的键值对是全局作用域的所有内容
print(locals())  # 因为当前作用域就是全局作用域,所以此时同 globals 返回的字典相同
posted @ 2022-10-07 20:30  I'm_江河湖海  阅读(0)  评论(0编辑  收藏  举报