Python闭包函数和装饰器

2018年7月2日笔记

7.Python函数对象和闭包

1.函数对象

函数是对象,可以给函数增加属性

def funcF(x,y,z):
    print(x,y,z)
funcF(1,2,3)
funcF.abc = "hello python"
print(funcF.abc

上面一段代码的运行结果如下:

1 2 3
hello python

2.函数闭包

1.概念:在一个外函数中定义了一个内函数,内函数运用了外函数的临时变量,并且外函数的返回值是内函数的引用
示例代码:演示函数嵌套和闭包。

def outer(a):
    b = 10
    def inner():
        print(a+b)
    return inner

demo = outer(5)
demo()

上面一段代码的运行结果如下:

15

8.Python装饰器

1.定义

装饰器实质上是一个Python函数,它可以让其他函数在不需要做任何代码变动的前提下增加额外功能,装饰器的返回值也是一个函数对象。他经常用于有切面需求的场景,比如:插入日志、性能测试、事务处理、缓存、权限校验等场景。装饰器是解决这类问题的绝佳设计,有了装饰器,我们就可以抽离出大量与函数功能本身无关的雷同代码并继续重用。概括的讲,装饰器的作用就是为已经存在的对象添加额外的功能。

2.场景

2.1 通过变量也能调用该函数

def hello():
    print("我是最初的hello函数")
#函数也是一个对象,而且函数对象可以赋值给变量
f = hello
f()

上面一段代码的运行结果如下:

我是最初的hello函数

2.2 场景
函数对象有一个name属性,可以获取函数的名字

def hello():
    print("我是最初的hello函数")

#获取函数的名字
print(hello.__name__)

上面一段代码的运行结果如下:

hello

2.3 假设增加hello()函数的功能,而完全不改变原来的代码

def outer(func):
    def inner(*args,**kwargs):
        print("我是%s()函数" %func.__name__)
        return func(*args,**kwargs)
    return inner

@outer
def hello():
    print("我是最初的hello函数")
hello()

上面一段代码的运行结果如下:

我是hello()函数
我是最初的hello函数

2.4 支持多个装饰器

import time

def deco1(func):
    print("deco1 decorated")
    def wrapper(*args, **kwargs):
        print("this is deco1")
        startTime = time.time()
        func(*args, **kwargs)
        endTime = time.time()
        ms = (endTime - startTime) * 1000
        print("time is %s ms" % ms)
        print("deco1 end here")
    return wrapper

def deco2(func):
    print("deco2 decorated")
    def wrapper(*args, **kwargs):
        print("this is deco2")
        func(*args, **kwargs)
        print("deco2 end here")
    return wrapper

@deco1
@deco2
def func(a, b):
    print("hello, here is func for add:")
    time.sleep(1)
    print("result is %d" % (a + b))

func(3, 4)

上面一段代码的运行结果如下:

deco2 decorated
deco1 decorated
this is deco1
this is deco2
hello, here is func for add:
result is 7
deco2 end here
time is 1000.9815692901611 ms
deco1 end here

多个装饰器使用的调用顺序:

def one(func):
    print('----1----')
    def two():
        print('----2----')
        func()
        print('----3----')
    return two

def a(func):
    print('----a----')
    def b():
        print('----b----')
        func()
        print('----c----')
    return b

@one
@a
def demo():
    print('----demo----')

demo()

上面一段代码的运行顺序如下:

----a----
----1----
----2----
----b----
----demo----
----c----
----3----

图片.png-18.5kB
图片.png-18.5kB

如上图所示,红色箭头标记“1”和“3”处越靠近函数的装饰器先被执行,红色箭头标记“2”处越远离函数的装饰器先被执行。

练习

1.定义一个函数,需求:去除列表中重复的元素.

def dropDuplicates(lt):
    new_list = []
    for i in lt:
        if i not in new_list:
            new_list.append(i)
    return new_list
##第二种方法一行代码解决
def dropDuplicates2(lt):
    return list(set(lt))

2.定义一个函数,需求:合并两个列表

def concatList(lt1,lt2):
    return lt1 + lt2

def concatList2(lt1,lt2):
    lt1.extend(lt2)
    return lt1

def concatList3(lt1,lt2):
    for i in lt2:
        lt1.append(i)
    return lt1

3.定义函数,需求:判断三个数中的最大值

def my_max(*args):
    return max(*args)

def my_max1(*args):
    max_number = args[0]
    for i in args:
        if i > max_number:
            max_number = i
    return max_number

4.定义一个函数,需求:实现斐波那契数列

def fibonacci(length):
    if length < 1:
        print("参数应该为正整数")
    if length == 1:
        return [1]
    elif length == 2:
        return [1,1]
    lt = [1,1]
    for i in range(2,length):
        lt.append(lt[i-1] + lt[i-2])
    return lt

5.将下列字符串变成字典

t = "k:1|k1:2|k2:3|k3:4"
result = {x:y for x,y in [k.split(':') for k in t.split('|')]}
print(result)

字符串函数

s = 'i love You so much'

print(s.ljust(22, '*'))
print(s.rjust(22, '2'))
print(s.center(22, '*'))
print(s.zfill(22))
print(s.replace('u', '1', 1))
print(s.split(' '))
print(s.upper())
print(s.lower())
print(s.capitalize())
print(s.title())
print(s.swapcase())
print(s.count('o'))
print(s.startswith('i'))
print(s.endswith('!'))
print(s.isalnum())
print(s.isalpha())
print(s.islower())
print(s.isupper())
print(s.istitle())

上面一段代码的运行结果如下:

i love You so much****
2222i love You so much
**i love You so much**
0000i love You so much
i love Yo1 so much
['i', 'love', 'You', 'so', 'much']
I LOVE YOU SO MUCH
i love you so much
I love you so much
I Love You So Much
I LOVE yOU SO MUCH
3
True
False
False
False
False
False
False
最后编辑于
©著作权归作者所有,转载或内容合作请联系作者
  • 序言:七十年代末,一起剥皮案震惊了整个滨河市,随后出现的几起案子,更是在滨河造成了极大的恐慌,老刑警刘岩,带你破解...
    沈念sama阅读 158,117评论 4 360
  • 序言:滨河连续发生了三起死亡事件,死亡现场离奇诡异,居然都是意外死亡,警方通过查阅死者的电脑和手机,发现死者居然都...
    沈念sama阅读 66,963评论 1 290
  • 文/潘晓璐 我一进店门,熙熙楼的掌柜王于贵愁眉苦脸地迎上来,“玉大人,你说我怎么就摊上这事。” “怎么了?”我有些...
    开封第一讲书人阅读 107,897评论 0 240
  • 文/不坏的土叔 我叫张陵,是天一观的道长。 经常有香客问我,道长,这世上最难降的妖魔是什么? 我笑而不...
    开封第一讲书人阅读 43,805评论 0 203
  • 正文 为了忘掉前任,我火速办了婚礼,结果婚礼上,老公的妹妹穿的比我还像新娘。我一直安慰自己,他们只是感情好,可当我...
    茶点故事阅读 52,208评论 3 286
  • 文/花漫 我一把揭开白布。 她就那样静静地躺着,像睡着了一般。 火红的嫁衣衬着肌肤如雪。 梳的纹丝不乱的头发上,一...
    开封第一讲书人阅读 40,535评论 1 216
  • 那天,我揣着相机与录音,去河边找鬼。 笑死,一个胖子当着我的面吹牛,可吹牛的内容都是我干的。 我是一名探鬼主播,决...
    沈念sama阅读 31,797评论 2 311
  • 文/苍兰香墨 我猛地睁开眼,长吁一口气:“原来是场噩梦啊……” “哼!你这毒妇竟也来了?” 一声冷哼从身侧响起,我...
    开封第一讲书人阅读 30,493评论 0 197
  • 序言:老挝万荣一对情侣失踪,失踪者是张志新(化名)和其女友刘颖,没想到半个月后,有当地人在树林里发现了一具尸体,经...
    沈念sama阅读 34,215评论 1 241
  • 正文 独居荒郊野岭守林人离奇死亡,尸身上长有42处带血的脓包…… 初始之章·张勋 以下内容为张勋视角 年9月15日...
    茶点故事阅读 30,477评论 2 244
  • 正文 我和宋清朗相恋三年,在试婚纱的时候发现自己被绿了。 大学时的朋友给我发了我未婚夫和他白月光在一起吃饭的照片。...
    茶点故事阅读 31,988评论 1 258
  • 序言:一个原本活蹦乱跳的男人离奇死亡,死状恐怖,灵堂内的尸体忽然破棺而出,到底是诈尸还是另有隐情,我是刑警宁泽,带...
    沈念sama阅读 28,325评论 2 252
  • 正文 年R本政府宣布,位于F岛的核电站,受9级特大地震影响,放射性物质发生泄漏。R本人自食恶果不足惜,却给世界环境...
    茶点故事阅读 32,971评论 3 235
  • 文/蒙蒙 一、第九天 我趴在偏房一处隐蔽的房顶上张望。 院中可真热闹,春花似锦、人声如沸。这庄子的主人今日做“春日...
    开封第一讲书人阅读 26,055评论 0 8
  • 文/苍兰香墨 我抬头看了看天上的太阳。三九已至,却和暖如春,着一层夹袄步出监牢的瞬间,已是汗流浃背。 一阵脚步声响...
    开封第一讲书人阅读 26,807评论 0 194
  • 我被黑心中介骗来泰国打工, 没想到刚下飞机就差点儿被人妖公主榨干…… 1. 我叫王不留,地道东北人。 一个月前我还...
    沈念sama阅读 35,544评论 2 271
  • 正文 我出身青楼,却偏偏与公主长得像,于是被迫代替她去往敌国和亲。 传闻我的和亲对象是个残疾皇子,可洞房花烛夜当晚...
    茶点故事阅读 35,455评论 2 266

推荐阅读更多精彩内容

  • 第2章 基本语法 2.1 概述 基本句法和变量 语句 JavaScript程序的执行单位为行(line),也就是一...
    悟名先生阅读 4,055评论 0 13
  • Spring Cloud为开发人员提供了快速构建分布式系统中一些常见模式的工具(例如配置管理,服务发现,断路器,智...
    卡卡罗2017阅读 134,099评论 18 139
  • Lua 5.1 参考手册 by Roberto Ierusalimschy, Luiz Henrique de F...
    苏黎九歌阅读 13,517评论 0 38
  • 【北京日记】 鸡毛蒜皮,仅供娱乐,不供探讨 一年很长,长到我可以体验三份工作,换三个房子 一年很短,短到我反省自己...
    喂马去了阅读 492评论 0 0
  • 我的理想 每个人都有理想,它们是生活道路的指路标,是黑夜的照明灯。有人人只有一个理想,他会为它一直奋斗,努力去实现...
    依然如水阅读 298评论 0 0