Welcome to kimi's blog

名称空间、全局变量、闭包函数

函数多种方法

名称空间

    name = 'kiki'
    
底层原理:
    1.申请内存空间存储kiki
    2.给kiki绑定一个变量名name
    3.后续通过变量名name就可以访问到kiki

​ 名称空间就是用来存储变量名与数据值绑定关系的地方(简单理解为存储变量名的地方)

名称空间分类

​ 名称空间分为内置名称空间和全局名称空间

	1.内置名称空间
		解释器运行自动产生,里面包含了很多名字
		eg:len print input
		
	2.全局名称空间
		py文件运行产生,里面存放文件级别的名字
            name = 'kiki'

            if name:
                age = 18

            while True:
                gender = 'female'

            def index():
                pass

            class MyClass(object):
                pass
                
     name\age\gender\index\MyClass
    
	3.局部名称空间
		函数体代码运行\类体代码运行  产生的空间

名称空间存货周期及作用范围(域)

存活周期

内置名称空间
	python解释器启动则创建,关闭则销毁
全局名称空间
	py文件执行则创建,运行结束则销毁
局部名称空间
	函数体代码运行则创建,函数体代码结束则销毁
		

作用域

内置名称空间
	解释器级别的全局有效
全局名称空间
	py文件级别的全局有效
局部名称空间
	函数体代码内有效

名字的查找顺序

​ 设计到名字的查找,一定要先搞明白自己在哪个空间

​ 1.当我们在局部名称空间中的时候,查找的顺序如下
​ 局部名称空间>>>全局名称空间>>>内置名称空间

​ 2.当我们在全局名称空间中的时候,查找的顺序如下

​ 全局名称空间>>>内置名称空间

​ 注意:其实名字的查找是可以的

image

查找顺序案例

1.相互独立的局部名称空间默认不能互相访问


    def demo():
        name = 'kiki'
        print(age)

    def demo():
        age = 18
        print(name)

2.局部名称空间嵌套

​ 先从自己的局部名称空间查找,之后由内而外依次查找

正确版本:

eg1:
goal = '每天能够准时吃饭!!!'
def demo():
    goal = '每天按时完成博客!!'
    def demo1():
        goal = '每天按时完成录音!!'
        def demo2():
            goal = '每天按时完成作业!!'
            def demo3():
                goal = '剩余时间预习第二天课程!!'
            demo3()
        demo2()
    demo1()
demo()

print(goal)  # 每天能够准时吃饭!!!

图如下


错误版本:

eg:
goal = '每天能够准时吃饭!!!'
def demo():
    goal = '每天按时完成博客!!'
    def demo1():
        goal = '每天按时完成录音!!'
        def demo2():
            demo2()
            goal = '每天按时完成作业!!'

            def demo3():
                # goal = '剩余时间预习第二天课程!!'
            demo3()
        
    demo1()
demo()
print(goal)  # IndentationError: expected an indented block  直接报错

""
"函数体代码中名字的查找顺序在函数定义阶段就已经固定死了
"""

上述例题查找的顺序如下

image

global与nonlocal关键字

1.global的用法

1.当不使用global时
	number = 89
    def index():
        
    	number = 34

    index()
    print(number)  # 89
        		
	
2.使用了global
	number = 89
    def index():
        global number
        number = 34
        
	index()
    print(number)  # 34
        
   """
      局部名称空间直接修改全局名称空间中的数据
   """

2.nonlocal的用法

1.当不使用nonlocaldef index():
	name = 'kiki'
        def inner():
            name = 'kimi'
        inner()
        print(name)  # kiki
    index()


2.当使用了nonlocal
    def index():
        name = 'kiki'
        def inner():
            nonlocal name
            name = 'kimi'
        inner()
        print(name)  # kimi
    index()

    """
    内层局部名称空间修改外层局部名称空间中的数据
    """

函数名的多种用法

​ 函数名其实绑定的也是一块内存地址,只不过该地址里面存在的不是数据值,而是一段代码,函数名加括号就会找到代码并执行。函数对象指的是可以被当作‘数据’来处理,具体可分为四个方面的使用

1.可以当作变量名赋值

    def index():
        pass

    res = index
    res()   # res() == index()
    print(res)  # <function index at 0x00000213D09461F0>

2.可以当做函数的参数

    def index():
        print('今天是10月11号')
    def func(a):
        print(a)  # a=index  <function index at 0x000002CCA40E61F0>
        a()  # a()==index()   直接调用index()  输出 ‘今天是10月11号’
    func(index)

3.可以当作函数的返回值

1.返回值返回第一个函数名

    def index():
        print('天气晴')

    def func():
        print('适合出门')
        return index

    res = func()   # 第一步看赋值的右边,调用func()函数输出‘适合出门’,返回index函数名给res
    print(res)  # 打印出index的函数名的内存地址  <function index at 0x0000028E8C7361F0>
    res()  # res() == index()   直接调用index()函数,输出‘天气晴’

2.返回值返回第二个函数名
    def index():
        print('天气晴')

        def func():
            print('适合出门')
        return func

    res = index()   # 第一步看赋值的右边,调用index()函数输出‘天气晴’,然后到return返回func
    print(res)  # 打印出func的函数名内存地址  <function index.<locals>.func at 0x000002876A56A4C0>
    res()  # res() == func()   直接调用func()函数,输出‘适合出门’

4.可以当作容器类型(可以存放多个数据的数据类型)的数据

​ 1.第一种方式----基础版


    def register():
        print('注册功能')

    def login():
        print('登录功能')

    def withdraw():
        print('提现功能')

    def transfer():
        print('转账功能')

    def shopping():
        print('购物功能')


    while True:
        print("""
        1.注册功能
        2.登录功能
        3.提现功能
        4.转账功能
        5.购物功能
        """)
        choice = input('please input your choice>>>:').strip()
        if choice == '1':
            register()
        elif choice == '2':
            login()
        elif choice == '3':
            withdraw()
        elif choice == '4':
            transfer()
        elif choice == '5':
            shopping()
        else:
            print('查无编号!!!!')
        
     

​ 2.第二种方式-----升级版

    def register():
        print('注册功能')

    def login():
        print('登录功能')

    def withdraw():
        print('提现功能')

    def transfer():
        print('转账功能')

    def shopping():
        print('购物功能')

    demo_dict = {
        '1':register,
        '2':login,
        '3':withdraw,
        '4':transfer,
        '5':shopping
    }


    while True:
        print("""
        1.注册功能
        2.登录功能
        3.提现功能
        4.转账功能
        5.购物功能
        """)
        choice = input('please input your choice>>>:').strip()
        if choice in demo_dict:
            # demo_dict.get(choice)()
            name = demo_dict.get(choice)
            name()
        else:
            print('查无编号')

闭包函数

定义在函数内部的函数,并且用到了外部函数名称空间中的名字

​ 1.定义在函数内部

​ 2.用到外部函数名称空间中的名字

    def demo():
        name = 'kiki'
        def inner():
            print(name)
    """   第二个函数里name用到了第一个函数name,称为闭包函数    """

闭包函数实际应用:是另外一种给函数体代码传参的方式

方式1:给函数体代码传参(代码里面缺什么变量名形参里面就补什么变量名)

    def stu_class(name,age):
        print(f"""
        姓名:{name}
        年龄:{age}
        """)
    stu_class('kimi',18)
    
    """ 这种方式,输入一次参数就打印出的结果只有一个"""

方式2:闭包函数

    def stu_class(name,age):
        # name = 'kiki'
        # age = 18
        def register():
            print(f"""
            姓名:{name}
            年龄:{age}
            """)
        return register
    res = stu_class('kiki',18)
    res()
    res()
    res = stu_class('kimi',20)
    res()
    res()

    """ 这种可以连续输出好几个信息"""
    对比信息图如下

解析步骤如下:

image

对比信息图如下

image

作业

   1..判断下列money的值是多少并说明理由 思考如何修改而不是新增绑定关系
	money = 100
	def index():
             money = 666	
 	print(money)
    
 答:money输出结果为100,第一步money绑定100,接下走def index(),函数体代码不走,print输出的时全局名称空间的money。
 

	money = 100
 	def func1():
            money = 666
        def func2():
            money = 888
        func2()
   print(money)
   							
   	答案:money 为100,func1为调用,此时的money还是全局名称空间的money
   
posted @   魔女宅急便  阅读(61)  评论(2编辑  收藏  举报
相关博文:
阅读排行:
· 全程不用写代码,我用AI程序员写了一个飞机大战
· MongoDB 8.0这个新功能碉堡了,比商业数据库还牛
· 记一次.NET内存居高不下排查解决与启示
· DeepSeek 开源周回顾「GitHub 热点速览」
· 白话解读 Dapr 1.15:你的「微服务管家」又秀新绝活了
Title
点击右上角即可分享
微信分享提示

目录导航