1,函数名的使用。
函数名是函数的名字,本质就是变量,特殊的变量。函数名()加括号就是执行此函数。
1,单独打印函数名就是此函数的内存地址。
def func1(): print(555) print(func1) # <function func1 at 0x0000027B7CF1A048>
2,函数名的赋值
def func(): print(666) f = func print(f())
3,函数名可以作为容器类数据的元素。
def f1(): print(111) def f2(): print(222) def f3(): print(333) def f4(): print(444) li = [] for i in range(1,5): li.append(‘f‘+str(i)) for i in li: eval(i)()
4,函数名可以作为参数。
def f1(): print(666) def f2(x): x() f2(f1)
5,函数名可以作为函数的返回值。
def f1(): print(666) def f2(x): return x f2(f1)()
函数又叫第一类对象(first-class object)指
1,可在运行期创建
2,可用作函数参数或返回值
3,可存入变量的实体。
2,闭包的使用
内部函数包含对外部作用域而非全剧作用域变量的引用,该内部函数称为闭包函数
#函数内部定义的函数称为内部函数
def wraaper(): def inner(): print(444) return inner wraaper()() def wraaper(): def inner(): print(555) inner() wraaper()
判断闭包函数的方法__closure__
def wraaper(): name = ‘taibai‘ def inner(): print(name) inner() print(inner.__closure__) wraaper()
#taibai
(<cell at 0x0000025B34990B58: str object at 0x0000025B34E14848>,)
name = ‘老男孩‘ def wraaper(n): def inner(): print(n) inner() print(inner.__closure__) wraaper(name)
老男孩
(<cell at 0x0000024AF7810B58: str object at 0x0000024AF8343990>,)
这个也是闭包。
闭包的作用,当函数开始执行时,如果遇到闭包,它有一个机制,它会永远开辟一个内存空间,将闭包中的变量等值放入其中,不会随函数的执行完毕而消失。
from urllib.request import urlopen content = urlopen(‘http://www.cnblogs.com/jin-xin/‘).read().decode(‘utf-8‘) print(content)
from urllib.request import urlopen def index(): ur1 =‘http://www.xiaohua100.cn/index.html‘ def get(): return urlopen(ur1).read() return get() print(index()())
3,装饰器
装饰器本质上就是一个python函数,他可以让其他函数在不需要做任何代码变动的前提下,增加额外的功能,装饰器的返回值也是一个函数对象。
装饰器的应用场景:比如插入日志,性能测试,事务处理,缓存等等场景。
现在我有一个需求,我想让你测试这个函数的执行时间,在不改变这个函数代码的情况下:
import time def func1(): print(‘所有痛苦都会过去‘) def timmer(f): def inner(): start_time = time.time() f() time.sleep(0.3) end_time = time.time() print(‘此函数的执行效率%s‘%(end_time - start_time)) return inner func1 = timmer(func1) func1()
但是如果有多个函数,我都想让你测试他们的执行时间,你每次是不是都得func1 = timer(func1)?这样还是有点麻烦,因为这些函数的函数名可能是不相同,有func1,func2,graph,等等,所以更简单的方法,python给你提供了,那就是语法糖。
import time def timmer(f): def inner(): start_time = time.time() f() time.sleep(0.3) end_time = time.time() print(‘此函数的执行效率%s‘%(end_time - start_time)) return inner @timmer def func1(): print(‘继续努力加油自己‘) func1()
import time def timmer(f): def inner(*args,**kwargs): start_time = time.time() ret = f(*args,**kwargs) time.sleep(0.3) end_time = time.time() print(‘此函数的执行效率%s‘%(end_time - start_time)) return ret return inner @timmer def func1(a,b): print(‘继续努力加油自己‘) return 666 print(func1(1,2))
装饰器的开放关闭原则:
1.对扩展是开放的
为什么要对扩展开放呢?
我们说,任何一个程序,不可能在设计之初就已经想好了所有的功能并且未来不做任何更新和修改。所以我们必须允许代码扩展、添加新功能。
2.对修改是封闭的
为什么要对修改封闭呢?
就像我们刚刚提到的,因为我们写的一个函数,很有可能已经交付给其他人使用了,如果这个时候我们对其进行了修改,很有可能影响其他已经在使用该函数的用户。
装饰器完美的遵循了这个开放封闭原则。