python 基础:函数(二)

本文主要探讨Python函数的各个方面,包括默认参数的陷阱、命名空间(内置、全局、局部)、函数执行、作用域规则、局部与全局变量的交互、函数嵌套与作用域链、函数作为第一类对象的概念以及闭包的原理和应用。通过深入理解这些概念,有助于提升Python编程能力。
摘要由CSDN通过智能技术生成

一. 知识仓库

  1. 默认参数的陷阱:如果默认参数的值是一个可变数据类型,那么每次调用的时候不传值,就公用这个数据类型的资源
  2. 函数的命名空间
    1、内置命名空间:
    - python解释器一启动就将可以使用的名字存储在内置命名空间中,内置的名字(如print、input、str…)在启动解释器的时候被加载进内存中
    - 与python解释器有关
    2、全局命名空间:
    - 是在程序从上到下被执行的过程中依次加载进内存的,放置了我们设置的所有变量名和函数名
    - 与我们写的代码有关,但不包括函数中的代码
    3、局部命名空间:
    - 是函数内部定义的名字,在函数被调用的时候才会产生这个名称空间,函数执行结束后该空间被回收(消失)
    - 与函数内部的名义有关
    4、注意:
    - 在局部:可以使用全局、内置命名空间中的名字
    - 在全局:可以使用内置命名空间中的名字,但是不能使用局部命名空间中的名字(函数执行结束后该空间被回收)
    - 在内置:不能使用局部、全局命名空间中的名字(在读代码和调用函数之前就已经启动了)
    - 依赖倒置原则:小的可以依赖大的,但大的不能依赖小的。该处内置为大,局部为小。
    - 当我们在全局定义了和内置空间中同名的名字时,会使用全局的名字(即当自己有的时候,就不找自己的上级要,一直到内置也没有该名字,就报错)
    - 局部和全局命名空间只有一个,而局部命名空间可能有多个(多个函数),且各个局部命名空间中的名字不共享,是相互隔离的
  3. 函数的执行(调用):func()本质上是函数的内存地址+(),即函数的内存地址(),而外在表现的func刚好指向了该函数的内存地址(见function_2.py)
  4. 作用域
    1、全局作用域:作用在全局,内置和全局命名空间中的名字属于全局作用域
    2、局部作用域:作用在局部,函数(局部空间)中的名字属于局部作用域
    3、注意:
    - 对于不可变数据类型,在局部可以查看全局作用域中的变量,但不能直接去修改,修改则需要在程序的一开始添加global声明)(见function_2.py)
    - 如果在一个布局(函数)内声明了一个global变量,那么这个变量在局部的所有操作将对全局的变量有效,出于安全应该避免使用global
  5. 两个方法:locals() ——> 查看该方法所在作用域中的所有名字、globals() ——> 查看全局作用域中的所有名字(内置命名空间+全局命名空间)
  6. 函数的嵌套和作用域链
    1、函数的嵌套调用:在函数里面调用函数
    2、函数的嵌套定义:
    - 内部的函数可以使用外部函数的变量
    - 内部函数在定义之后需要进行调用,否则会在外部函数调用之后消失而不产生作用
    - 同样的,对于不可变数据类型,内部函数只可以使用外部变量,但不可修改
    - 如果内部函数用到global则是修改全局变量,也不会对外部函数(局部)定义的a产生作用(见function_2.py)
    - 内部函数修改外部函数的变量:使用 nonlocal 进行声明,其作用范围是向上找到的第一个该局部变量(注意局部!),到最外层局部也找不到就报错
  7. 函数名的本质
    1、函数名本质上就是指向该函数的一段内存地址
    2、函数名是第一类对象
    - 函数名可以作为函数的返回值和参数
    - 函数名可以作为容器类型的元素
    - 函数名可以赋值
    3、第一类对象(first-class object)
    - 可在运行期创建
    - 可用作函数参数或返回值
    - 可存入变量的实体
  8. 闭包
    1、条件:嵌套函数,内部函数调用外部函数的变量
    2、常见的闭包的使用方法:在一个函数的外部去使用这个函数内部的函数
    3、使用闭包的好处:保护了局部变量,减少了局部变量频繁的创建和消散而造成的浪费
    二. 代码练习
"""
默认参数的陷阱
- 如果默认参数的值是一个可变数据类型,那么每次调用的时候不传值,就公用这个数据类型的资源
"""
def func1(l1=[]):
    l1.append(1)
    print(l1)
func1()     # [1]
func1([])   # [1]
func1()     # [1, 1]
func1()     # [1, 1, 1]
# 列表是可变数据类型

def func2(k, dic1={
    }):
    dic1[k] = 'v'
    print(dic1)
func2
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值