写代码要遵循开发封闭原则,虽然在这个原则是用的面向对象开发,但是也适用于函数式编程,简单来说,它规定已经实现的功能代码不允许被修改,但可以被扩展,即:

封闭:已实现的功能代码块
开放:对扩展开发

#s2.py

def outer(func):
def inner():
print("log")
return func()
return inner @outer
def f1():
print("F1") @outer
def f2():
print("F2") @outer
def f100():
print("F100") #b1.py
import s2 s2.f1()
s2.f2()

一、装饰器流程剖析储备知识:

1、
def f1():
print('123') def f1():
print('456') f1() 2、
def f1():
print('123') def f2(xxx):
xxx() f2(f1)

 二、装饰器流程剖析:

def outer(func):
def inner():
print('before')
func()
print('after')
return inner @outer
def f1():
print("F1")

# @ + 函数名
# 功能
# 1. 自动执行outer函数并且将其下面的函数名f1当作参数传递
# 2. 将outer函数的返回值,重新复制给 f1

# 定义函数,为调用,函数内部不执行
# 函数名 》 代指函数

三、装饰器流程剖析之返回值:

# s1.py

def outer(func):
def inner():
print('before')
r = func()
print('after')
return r
return inner @outer
def f1():
print("F1")
return "nini" @outer
def f2():
print("F2") # b1.py
import s2 ret = s2.f1()
print("返回值",ret)

注:return 不能先执行,如果先执行后面的操作将不会操作,所以return放在最后。

四、装饰器流程剖析之参数:

# s1.py

def outer(func):
def inner(a):
print('before')
r = func(a)
print('after')
return r
return inner @outer
def f1(arg):
print(arg)
return "nini" # b1.py import s2 ret = s2.f1('faffa')
print("返回值",ret)

多参数传递,万能参数:

#s1.py

def outer(func):
def inner(*args,**kwargs):
print('before')
r = func(*args,**kwargs)
print('after')
return r
return inner @outer
def f1(arg):
print(arg)
return "nini" @outer
def f2(a1,a2):
print("F2") #b1.py
import s2 ret = s2.f1('faffa')
print("返回值",ret) s2.f2(11,22)

五、实例:用户管理程序:

装饰器最常用的功能之一是可以做权限的验证

LOGIN_USER = {"is_login":False}

def outer(func):
def inner(*args,**kwargs):
if LOGIN_USER['is_login']:
r = func()
return r
else:
print("请登录")
return inner @outer
def order():
print("欢迎%s登录" % LOGIN_USER['current_user']) @outer
def changepwd():
print("欢迎%s登录" % LOGIN_USER['current_user']) @outer
def manager():
print("欢迎%s登录" % LOGIN_USER['current_user']) def login(user,pwd):
if user == "alex" and pwd == "123":
LOGIN_USER['is_login'] = True
LOGIN_USER['current_user']=user
manager() def main():
while True:
inp = input("1,后台管理; 2,登录")
if inp == '1':
manager()
elif inp == '2':
username = input("请输入用户名")
pwd = input("请输入密码")
login(username,pwd) main()

六、双层装饰器实现用户登录和权限验证:

逻辑:多层装饰器,是从下往上一步步执行得。

#!/usr/bin/env python
# -*- coding: utf-8 -*- USER_INFO = {} def check_login(func):
def inner(*args,**kwargs):
if USER_INFO.get('is_login', None):
ret = func(*args,**kwargs)
return ret
else:
print('请登录')
return inner def check_admin(func):
def inner(*args,**kwargs):
if USER_INFO.get('is_login', None):
if USER_INFO.get('user_type', None) == 2:
ret = func(*args,**kwargs)
return ret
else:
print('无权限查看')
else:
print('请登录')
return inner @check_login
@check_admin
def index():
"""
管理员的功能
:return:
"""
print('Index') @check_login
def home():
"""
普通用户的功能
:return:
"""
print('home') def login():
user = input('请输入用户名:')
if user == 'admin':
USER_INFO['is_login'] = True
USER_INFO['user_type'] = 2
else:
USER_INFO['is_login'] = True
USER_INFO['user_type'] = 1 def main():
while True:
inp = input('1、登录;2、查看信息;3、超级管理员管理 \n >>> ')
if inp == "1":
login()
elif inp =='2':
home()
elif inp == '3':
index() main()

参考自:http://www.cnblogs.com/wupeiqi/articles/4980620.html

Python开发【第一篇】Python基础之装饰器的更多相关文章

  1. Python开发 第一篇 python的前世今生

    Python前世今生 python的创始人为吉多·范罗苏姆(Guido van Rossum).1989年的圣诞节期间,吉多·范罗苏姆为了在阿姆斯特丹打发时间,决心开发一个新的脚本解释程序,作为ABC ...

  2. Python【第一篇】基础介绍

    一.本节主要内容 Python介绍 发展史 Python 2 or 3? 安装 Hello World程序 变量 用户输入 模块初识 .pyc文件 数据类型初识 数据运算 表达式if ...else语 ...

  3. python开发第一篇:初识python

    一. Python介绍 python的创始人为吉多·范罗苏姆(Guido van Rossum).1989年的圣诞节期间,吉多·范罗苏姆为了在阿姆斯特丹打发时间,决心开发一个新的脚本解释程序,作为AB ...

  4. Python开发——7.迭代器、生成器和装饰器

    一.迭代器 1.迭代器协议 (1)迭代器协议是指:对象必须提供一个next方法,执行该方法要么返回迭代中的下一项,要么引起一个StopIteration移除异常以中止迭代. (2)可迭代对象:实现了迭 ...

  5. Python开发第一篇

    Python 是什么? 首先他可能是比较好的一个编程开发语言!

  6. Python unittest第一篇:基础入门+命令行编译

    unittest单元测试框架最初受JUnit启发,与其他语言的主要单元测试框架具有相似的风格. 它支持测试自动化,支持开启或关闭某个测试,支持结合测试.另外它可以生成各个单元测试的报告.为了实现以上功 ...

  7. 图解Python 【第一篇】:Python基础1

    本节内容一览图 一.Python简介  Python前世今生 python的创始人为吉多·范罗苏姆(Guido van Rossum).1989年的圣诞节期间,吉多·范罗苏姆为了在阿姆斯特丹打发时间, ...

  8. 各位大佬Python的第一部分道基础题已经整理好了,希望大家面试的时候能用的上。

    Python的第一部分道基础题,希望大家面试的时候能用的上. 1.为什么学习Python? Python是目前市面上,我个人认为是最简洁.最优雅.最有前途.最全能的编程语言,没有之一. 2.通过什么途 ...

  9. 《python开发技术详解》|百度网盘免费下载|Python开发入门篇

    <python开发技术详解>|百度网盘免费下载|Python开发入门篇 提取码:2sby  内容简介 Python是目前最流行的动态脚本语言之一.本书共27章,由浅入深.全面系统地介绍了利 ...

  10. python第一篇-------python介绍

    一.python介绍 python的创始人为吉多·范罗苏姆(Guido van Rossum).1989年的圣诞节期间,Guido开始写Python语言的编译器.Python这个名字,来自Guido所 ...

随机推荐

  1. Java基础知识强化106:Java中 int 的各进制之间的转换

    1.二.八.十.十六进制之间的转换  下面是示例代码,我们直接通过JDK工具库中的方法实现的,如下: public static Integer valueOf(String s, int radix ...

  2. 基于SocketAsyncEventArgs的版本

    文字水平差就慢慢开始练习,同时分享一下,项目中写的简单socket程序,不同方式的版本,今天上一个异步.可能实现高性能的处理方式.IOCP就不多说了,高性能的完成端口,可以实现套接字对象的复用,降低开 ...

  3. 【网络编程】之十二、wsaeventselect+线程池 服务器实现

    #include<WinSock2.h> #include<iostream> using namespace std; #pragma comment(lib, " ...

  4. Session共享的简单总结

    1.同服务器.同一域名.不同应用(端口.虚拟目录等) 这种很简单,把sessionState保存到SQLServer,aspnet_regsql之后,修改存储过程TempGetAppID,把 SET ...

  5. 【WinAPI】User32.dll注释

    #region User32.dll 函数 /// <summary> /// 该函数检索一指定窗口的客户区域或整个屏幕的显示设备上下文环境的句柄,以后可以在GDI函数中使用该句柄来在设备 ...

  6. javaweb学习总结二十六(response对象的用法二 下载文件)

    一:浏览器打开服务器上的文件 1:读取服务器上面的资源,如果在web层,可以直接使用servletContext,如果在非web层 可以使用类加载器读取文件 2:向浏览器写数据,实际上是把数据封装到r ...

  7. ps怎么给文字描边

    在设计的时候,单一的文字,往往对人没有多少的吸引力,这就需要我们在文字上加一些文字特效,比如说外发光,描边,投影,等等.在这里我们详细的介绍一下文字的输入,和文字描边的怎么增加,删除的经验.(这些方法 ...

  8. codeforces 676C C. Vasya and String(二分)

    题目链接: C. Vasya and String time limit per test 1 second memory limit per test 256 megabytes input sta ...

  9. hdu 2295 DLX

    思路:裸的DLX重复覆盖 #include<set> #include<cmath> #include<queue> #include<cstdio> ...

  10. JS辨别浏览器系统IOS或安卓

    详细内容请点击 /* * 智能机浏览器版本信息: * */ (function($,window,document){     $.extend({         browser:{         ...