python入门基础-三元表达式、命名空间、作用域、函数名本质、闭包

1.三元表达式(三目运算式)

#1 三元表达式(三目运算法)
#格式为: 为真时的结果 if 判定条件 else 为假时的结果
#另外三元表达式只适合较为简洁的条件判定,较为复杂的判定建议不要用这种方式写代码,因为比较让他人难以理解。

a = 10
b = 15

compare = a if  a > b else b    #谁大返回谁
print(compare)

2.命名空间(namespace)

#2 命名空间(namespace)
#命名空间是名称和对象的印象,也可以将命名空间理解成一个字典,例如定义变量的时候,变量名名就是对应字典的key,而后面的赋值内容就是字典的value,再举例说函数也是一样,函数名就是字典的key,函数体就是字典的value;
#各个命名空间是独立的,没有任何关系的,所以一个命名空间中不能存在重名,但不同的命名空间可以重名并且没有影响。
#在python当中命名空间分为内置空间、全局空间、局部空间三种。

#(1)python解释器拥有自己内置空间,内置的函数在解释器启动时就被加载到内存中,任何模块都可以访问它,它存放着函数和异常。
#(2)每个模块拥有它自已的命名空间,叫做全局命名空间,它记录了模块的变量,包括函数、类、其它导入的模块、模块级的变量和常量。
#(3)每个函数都有着自已的命名空间,叫做局部命名空间,它记录了函数的变量,包括函数的参数和局部定义的变量。

3.命名空间查找顺序

#3 命名空间查找顺序
# 假设查找当前命名空间中的“s”变量。
# (1)局部命名空间:首先在局部命名空间中查找,如果没有发现继续去上层全局命名空间查找,如果再没有继续向上层内置命名空间查找,如果再没有python会返回错误。
# (2)全局命名空间:首先在全局命名空间中查找,如果没有发现继续去上层内置命名空间查找,如果再没有python会返回错误。
# (3)内置命名空间:如果在内置命名空间差找不到,直接返回错误。

#1)局部命名空间内调用全局命名空间的变量:
a = 10
def my():
    print(a)    #可以成功打印出来10

my()

#如果换成这样就不能调用了:
a = 10
def my():
    a += 1  #对于不可变类型在局部命名空间中可以查看,但不能直接去修改。
    #错误:UnboundLocalError: local variable ‘a‘ referenced before assignment
    print(a)    #可以成功打印出来10

my()

#在全局命名空间调用内置命名空间的变量:
x = 10
def my(x):  # x = 15
    print(x)    # x =15

my(15)
print(x)    # x = 10,全局命名空间只会在当前或上级内置命名空间中查找x,不会去局部命名空间中查找x

4.作用域

#4 作用域
#作用域就是作用范围,按照生效范围可以分为全局作用域和局部作用域两种。
#(1)全局作用域:包含内置命名空间和全局命名空间,在整个文件中任意位置可以被引用,并且全局有效。
#(2)局部作用域:局部命名空间,只能在局部范围内有效。

5.globals和locals的区别

# 5 globals和locals的区别
#globals方法
#globals永远打印全局的名字
def a():
    print(globals())    #局部命名空间中的输出结果和全局命名空间中的输出结果一样

a()
print(globals())

#locals方法
#输出什么,根据locals所在位置决定。
def func():
    a = 10
    b = 12
    print(locals()) #打印的信息时局部命名空间的变量信息

func()
print(locals()) #打印的信息和globals一样

#global 关键字
#如果在局部命名空间中需要修改全局命名空间的变量值,需要在其之前用global声明即可,其后面的操作将对全局变量有效。

a = 12
def func():
    global a    #对变量a进行全局声明,之后的操作将对全局的变量有效
    a = 25
    print(a)    # a = 25 对全局变量有效

func()
print(a)    # a = 25

6.函数的嵌套和作用域

#6 函数的嵌套和作用域链
#(1)函数的嵌套调用
def my_compare1(a,b):       #顺序1
    return a if a > b else b    #顺序8    #顺序10

def my_compare2(a,b,c):     #顺序2
    c1 = my_compare1(a,b)   #顺序7
    return my_compare1(c,c1)    #顺序9

a = 10      #顺序3
b = 20      #顺序4
c = 15      #顺序5
print(my_compare2(a,b,c))       #顺序6    #顺序11 打印函数的返回值

#(2)函数的嵌套定义
def f1():       #顺序1
    print(‘in f1‘)      #顺序3
    def f2():       #顺序4
        print(‘in f2‘)      #顺序6
    f2()            #顺序5
f1()        #顺序2

#(3)函数的作用域链
#one

def f1():
    a = 1
    def f2():
        def f3():
            print(a)    #打印出的结果是 1 ,因为现在f3属于子局部命名空间,存在父局部命名空间,如果当前子局部域名空间没有,就会向上查找变量a,直至到内置命名空间。
        f3()
    f2()

f1()

#two

def f1():
    a = 1
    def f2():
        a = 2
    f2()
    print(‘a in f1 : ‘,a)   #此处的变量a,打印出来的是1,因为print和f2函数命名所处f1函数体中,而f2函数体中的a = 2 所处空间是print所在空间的子局部空间,所以print 打印 a的时候不会向下查找。
f1()

#(4)nonlocal关键字
#nonlocal 只能用于局部变量 找上层中离当前函数最近一层的局部变量
#声明了nonlocal的内部函数的变量修改会影响到 离当前函数最近一层的局部变量
a = 10
def f1():
    a = 1
    def f2():
        a = 2
        def f3():
            nonlocal a  #对变量声明nonlocal之后,后面对变量a的操作只会对上一层的局部变量有影响。
            a = 2 + 1
        f3()
        print(‘a in f2:‘,a)
    f2()
    print(‘a in f1 : ‘,a)

f1()
print(a)

7.函数名的本质

#7 函数名的本质
#函数名本质上就是函数的内存地址
#(1)可以被引用
def func():
    print(‘hello word!‘)
fun = func
fun()   #fun()和func()调用函数体之后,打印的信息完全一致
func()

#(2)可以被当作容器类的元素
def f1():
    print(‘f1‘)
def f2():
    print(‘f2‘)
def f3():
    print(‘f3‘)

l = [f1,f2,f3]
d = {‘f1‘:f1,‘f2‘:f2,‘f3‘:f3}
#调用
l[0]()  #调用f1函数体的内容
d[‘f2‘]()   #调用f2函数体的内容

#(3)可以当做函数的参数或返回值
#当参数
def func1():
    print(‘abc‘)

def func2(func1):
    func1()         #调用func1函数
    print(‘def‘)

func2(func1)    #将func1函数名当做参数传递给func2函数

#当返回值
def func1():
    print(‘abc‘)

def func2():
    print(‘def‘)
    return func1    #将func1函数名当做地址返回

a = func2() #将func1函数的内存地址复制给变量a
a() #调用func1函数

8.闭包

#8 闭包函数
#闭包(Closure)是词法闭包(Lexical Closure)的简称,是引用了自由变量的函数。这个被引用的自由变量将和这个函数一同存在
# ,即使已经离开了创造它的环境也不例外。所以,有另一种说法认为闭包是由函数和与其相关的引用环境组合而成的实体。(看起来相当难以理解)

#对于上面的解释,我总结闭包在嵌套函数的环境中,内部函数调用外部函数的变量,并且外部函数的变量一直存在,下面举个例子看看。
def func():
    a = 0
    print(‘输出外部函数的变量:‘,a)
    def f1():
        print(‘内部函数输出变量:‘,a)
    return  f1

f = func()
f()         #第一次调用会打印出来“输出外部函数的变量: 0” 和“内部函数输出变量: 0”
f()         #再次调用会打印出来“内部函数输出变量: 0”,包括后面无论几次调用,打印的结果都是这种,不会出现上面的情况,这就是闭包的方式之一

#判断闭包函数的方法__closure__
#输出的__closure__有cell元素 :是闭包函数
def func():
    name = ‘eva‘
    def inner():
        print(name)
    print(inner.__closure__)    #打印结果:(<cell at 0x00000221EB0A0B58: str object at 0x00000221EB8438F0>,)
    return inner

f = func()
f()

#输出的__closure__为None :不是闭包函数
name = ‘egon‘
def func2():
    def inner():
        print(name)
    print(inner.__closure__)    #因为外部函数体(局部空间)内不存在变量,所以打印结果:None
    return inner

f2 = func2()
f2()

原文地址:https://www.cnblogs.com/jason-lv/p/8127777.html

时间: 2024-10-03 02:58:26

python入门基础-三元表达式、命名空间、作用域、函数名本质、闭包的相关文章

Python入门基础学习 三

Python入门基础学习 三 数据类型 Python区分整型和浮点型依靠的是小数点,有小数点就是浮点型. e记法:e就是10的意思,是一种科学的计数法,15000=1.5e4 布尔类型是一种特殊的整形,true就相当于1,false相当于0,可以用来计算 类型转换 转换:整数:int();字符串:str();浮点数:float() 转换例子:(图9) 如果用内置函数当变量名,比如str=123,一旦被赋值,再使用这个函数会被报错. type()函数可以明确告诉我们变量类型. isinstance

Python学习路线引导-Python入门基础

一.学习目标和建议学习周期 1.学习目标:完成Python入门基础,为数据分析事或者软件测试工程师知识体系中Python编程的入门知识. 2.学习阶段:2020.1.13-2020.2.23六周,建议每周学习时长15小时,整个学习时长90小时. 二.推荐教程 廖雪峰教程:https://www.liaoxuefeng.com/wiki/1016959663602400 学习笔记:<Python入门学习笔记-精灵>-部分示例代码源自廖雪峰教程,可参照其教程,理解其知识点,在数据分析与软件测试创新

Python基础-----三元表达式、列表解析、生成器表达式

三元表达式: 变量 = 值1 if 条件为真 else 值2 类似于: res = '对了' if 1 > 2 else '错了' print(res) >>> '错了' 普通表示: if 1 > 2: print('对了') else: print('错了') 列表解析: 假如要生成0-9共10个数字,存放在列表中 类似于: l = [i for i in range(10)] print(l) >>> [0, 1, 2, 3, 4, 5, 6, 7, 8

python 全栈 python基础 (九)作用域 函数嵌套 闭包

名称空间与作用域 变量,函数 分成三种 #内置名称空间  内置函数, 系统函数内部自定义的. python查看内置函数,命令: import builtins dir(builtins) #全局名称空间  文件中 顶头写,没有任何缩进定义的函数或是变量. 定义之后,在整个文件的任何位置都可以用. #局部名称空间 定义之后,在局部环境内可以调用,例如在一个定义函数中定义的变量,只能在当前函数内部调用,往外全局或是其他函数均不能调用. 在外部,或是其他定义的函数调用的话,会报错! 内置和全局名称空间

python入门基础-函数装饰器的理解

1.装饰器 # 知乎某大神是这么比喻装饰器的:内裤可以用来遮羞,但是到了冬天他就没有办法为我们御寒,聪明的人于是发明了长裤,有了长裤后宝宝再也不冷了, # 装饰器就像我们这里说的长裤,在不影响内裤作用的前提下,给我们的身子提供了保暖的功效. # # 大神是将程序中原本的函数比喻成内裤,而装饰器比喻成了长裤,这样在寒冬里它们结合一起使用就给所有人带来了温暖. # # 装饰器本质上是一个python函数,它可以让其它函数在不改动代码的情况下增加额外的功能,并且装饰器的返回值也是一个函数对象. # 在

python之路---10 *args **kwargs 命名空间 作用域 函数的嵌套

二十八.函数进阶 1.   "*"  和  "**" ① 在形参位置时   都是聚合的作用 *args    位置参数→元组 **kwargs   关键字参数→字典 混合时顺序为: 位置  , *args ,  默认值 , **kwargs ② 在实参位置时    都是打散的作用 *args      字符串,元组,字典 → 位置参数 **kwargs     字典 → 关键字参数 2.名称空间    用来存放名字(变量, 函数名, 类名, 引入的模块名)的 1.

python基础-三元表达式/列表推导式/生成器表达式

1.三元表达式:如果成立返回if前的内容,如果不成立返回else的内容 name=input('姓名>>: ') res='SB' if name == 'alex' else 'NB' print(res) 2.列表推导式:l=['egg'+str(i) for i in range(1,11)] print(l) 3.生成器表达式: l=('egg'+str(i) for i in range(1,11) if i >6) for i in l: print(i) 原文地址:http

Python 入门基础11 --函数基础4 迭代器、生成器、枚举类型

今日目录: 1.迭代器 2.可迭代对象 3.迭代器对象 4.for循环迭代器 5.生成器 6.枚举对象 一.迭代器: 循环反馈的容器(集合类型) 每次重复即一次迭代,并且每次迭代的结果都是下一次迭代的初始值 l = [1, 2, 3] count = 0 while count<len(l): print(l[count]) count += 1 1.1 为什么要有迭代器? 字符串.列表.元组可以通过索引的方式迭代取出其中包含的元素 字典.集合.文件等类型,没有索引,只有通过不依赖索引的迭代方式

Python入门篇(六)之函数

1.函数 1.1.编程的方式: (1)面向对象 -->华山派 -->独门秘籍:类 -->定义关键字:class (2)面向过程 -->少林派 -->独门秘籍:过程 -->定义关键字:def (3)函数式编程 -->逍遥派 -->独门秘籍:函数 -->定义关键字:def 1.2.函数是什么? 函数是组织好的,可重复使用的,用来实现单一,或相关联功能的代码段. 函数能提高应用的模块性,和代码的重复利用率.你已经知道Python提供了许多内建函数,比如pri