Python课程回顾(day12)

装饰器

1.什么是装饰器

装饰器就是为被装饰对象增添新的功能,而装饰器本身就是可任意调用的对象,可以把装饰器看错一个函数,而被装饰对象也可以是任意可调用的对象。

2.为什么要用装饰器

没有十全十美的程序,所以我们在写出来一个个程序的时候要考虑到以后对程序本身功能的添加以便用户使用,而若是我们只根据需求去随意修改源代码,则与源代码有关联的一切代码都要被修改,麻烦且容易影响用户体验,所以我们的程序一旦上线就应该对修改关闭,对扩展开放。修改关闭即不能修改源代码及调用方式,扩展开放即可以在原有是功能上增添新的功能。

3.如何使用装饰器

 使用装饰为函数增添计时功能

import time     导入时间系统

def index():
    print('welcome to index page')
    time.sleep(3)

def outter(func):
    # func由于下面的intex赋值所以指向最原始那个index的内存地址                             
    def wrapper():
        start=time.time()
        func() # 指向最原始那个index的内存地址()将index调用使index拥有计时功能
        stop=time.time()
        print('run time is %s' %(stop-start)) 计算时间
    return wrapper将wrapper的值返回给outter
index=outter(index)  此时的index等于增添过新功能后的index
index() 内存地址已经指向wrapper,所以此刻调用index等同于调用wrapper,不过要遵循不改变调用方式所以还是只能掉index

装饰器修正

import time     导入时间系统

def index():
    print('welcome to index page')
    time.sleep(3)

def outter(func):               接上个功能
    def wrapper():              此时我们的wrapper里是没有参数的,假设我们需要传入参数的话可以使用*args与**kwargs来接收传入func的值
        start=time.time()
        res = func()            func会把值原封不动的赋值给res
        stop=time.time()
        print('run time is %s' %(stop-start)) 
    return wrapper
index=outter(index) 
index() 

装饰器语法糖

1.使用装饰器之前要知道,python执行程序是从上到下运行的,所以我们给一个功能使用装饰器的时候要记得,装饰器一定要在函数功能上方。

import time

def outter(func): def wrapper(): start=time.time() res = func() stop=time.time() print('run time is %s' %(stop-start)) return wrapper index=outter(index) index()

@outter 使用语法糖可以将index = outter(index)这一步给省略掉
def index():
  print('welcome to index page')
  time.sleep(3)

wraps

import time                                                 
from functools import wraps            在使用wraps之前导入wraps库

def outter(func):
    @wraps      (使用wraps可以将wrapper与index的各种属性全部合并,内存地址或名字无论查看index还是wrapper都是一样的)                     
    def wrapper():
        start=time.time()
        func() 
        stop=time.time()
        print('run time is %s' %(stop-start)) 
    return wrapper             
index=outter(index)  
index() 内存地址已经指向wrapper,所以此刻调用index等同于调用wrapper,不过要遵循不改变调用方式所以还是只能掉index


def index():
    print('welcome to index page')
    time.sleep(3)

无参装饰器与有参装饰器

def outter(func):                #func用于接收用户传进来的任意类型的值再赋值给res
    def wrapper(*args,**kwargs):
        res=func(*args,**kwargs)        (无参装饰器模板,由两层函数体组成)
        return res
    return wrapper

def auth():
x=111
def outter(func):
def wrapper(*args,**kwargs):
res=func(*args,**kwargs) (有参装饰器模板,由三层函数体组成,用于接收溢出的值)
return res
return wrapper
return outter


global与nonlocal

global:在局部声明变量是全局变量

x=1
def func():
    global x   此处声明x=2是全局变量
    x=2

nonlocal:在局部声明变量是外层函数的变量

x=333
def f1():
    x=222
    def f2():
        x=111
        def f3():
            nonlocal x     (此处声明x是def f3的变量,即调用f3则会打印x=0)
            x=0
        f3()
        print('f2内部的x: ',x)
    f2()
    print('这是f1内部的x: ',x)

f1()
print(x)

  

posted @ 2018-09-27 19:52  BlackLinks  阅读(119)  评论(0编辑  收藏  举报