偏函数在Python 2.5 版本中添加进来,是函数式编程一系列重要改进中的一部分。使用偏函数,可以通过有效地“冻结”那些预先确定的参数来缓存函数参数,然后在运行时,当获得需要的剩余参数后,可以将它们解冻,传递到最终的参数中,从而使用最终确定的所有参数去调用函数。
偏函数最好的一点是它不只局限于函数。偏函数可以用于可调用对象(任何包括函数接口的对象),只需要通过使用圆括号即可,包括类、方法或可调用实例。对于有很多可调用对象,并且许多调用都反复使用相同参数的情况,使用偏函数会非常合适。
GUI編程是一个很好的偏函数用例,因为你很可能需要GUI控件在外观上具有一致性,而这种一致性来自于使用相同参数创建相似的对象。我们现在要实现一个应用,这个应用中有很多按钮有相同的前景色和背景色,对于这种只有细微差别的按钮,使用相同的参数创建相同的实例简直是一种浪费:前景色和背景色都是相同的,只有文本有点不同。
交通路标示例:
# encode utf-8 from functools import partial as pto import tkinter as tk from tkinter.messagebox import showinfo, showwarning, showerror WARN = 'warn' CRIT = 'crit' REGU = 'regu' SIGNS = { 'do not enter': CRIT, 'railroad crossing': WARN, 'SS\nspeed limit': REGU, 'wrong way': CRIT, 'merging traffic': WARN, 'one way': REGU } critCB = lambda: showerror('Error', 'Error Button Pressed') #showerror, showwarnning showinfo 是tkinter自带的函数 ,我们用lambda 把函数赋值 warnCB = lambda: showwarning('Warnning', 'Warnning Button Pressed') infoCB = lambda: showinfo('info', 'Info Button Pressed') top = tk.Tk() top.title('Road Signs') MyButton = pto(tk.Button, top) CritButton = pto(MyButton, command=critCB, bg='white', fg='red') #偏函数式編程 WarnButton = pto(MyButton, command=warnCB, bg='goldenrod1') ReguButton = pto(MyButton, command=infoCB, bg='white') quit = tk.Button(top, command=top.quit, text='QUIT').pack(fill=tk.X, expand=True) for eachSign in SIGNS: signType = SIGNS[eachSign] cmd = '%sButton(text=%r%s).pack(fill=tk.X, expand=True)' % ( #把命令变成字符串,对于不同的按钮进行modification signType.title(), eachSign, '.upper()' if signType == CRIT else '.title()') eval(cmd) #利用eval ,运行字符串 tk.mainloop()
当我们运行这个程序时,会出现如下画面:
点击WRONG WAY按钮: