在Python中调用函数列表的惯用方法是什么?

时间:2009-05-22 11:09:54

标签: python

我有一个回调函数列表,我需要在触发事件时调用它。 这是惯用的蟒蛇吗?

def first_callback(m):
  print 'first ' + m

def second_callback(m):
  print 'second ' + m

lst = [first_callback, second_callback]

map(lambda x: x("event_info"),lst) #is this how you do it?

4 个答案:

答案 0 :(得分:17)

仅将map用于没有副作用的函数(例如print)。也就是说,仅将它用于只返回某些东西的函数。在这种情况下,常规循环更惯用:

for f in lst:
    f("event_info")

编辑:同样,从Python 3.0开始,map返回迭代器而不是列表。因此,在Python 3.0中,问题中给出的代码不会调用任何函数,除非显式评估生成器中的所有元素(例如,通过将调用封装到map list内)。幸运的是2to3工具会对此发出警告:

档案map.py

map(lambda x: x, range(10))

2to3-3.0 map.py输出:

RefactoringTool: Skipping implicit fixer: buffer
RefactoringTool: Skipping implicit fixer: idioms
RefactoringTool: Skipping implicit fixer: set_literal
RefactoringTool: Skipping implicit fixer: ws_comma
--- map.py (original)
+++ map.py (refactored)
@@ -1,1 +1,1 @@
-map(lambda x: x, range(10))
+list(map(lambda x: x, list(range(10))))
RefactoringTool: Files that need to be modified:
RefactoringTool: map.py
RefactoringTool: Warnings/messages while refactoring:
RefactoringTool: ### In file map.py ###
RefactoringTool: Line 1: You should use a for loop here

答案 1 :(得分:3)

你也可以写一个列表理解:

[f("event_info") for f in lst]

但是,它确实会产生返回结果列表的副作用。

答案 2 :(得分:0)

如果您已经动态创建了简单易用的函数列表:

for list_of_functions中的函数:     函数(your_argument_here)

但是如果你使用OOP并且某些类应该知道某些事件发生(通常是更改),请考虑引入Observer设计模式: http://en.wikipedia.org/wiki/Observer_pattern

引入模式意味着将工作代码重构为该模式(并在代码看起来很好时停止,即使没有引入整个模式)在“重构模式”Kerievsky中阅读更多内容。

答案 3 :(得分:0)

我不得不问这是否真的是OP的意图。当我听到“调用函数列表”时,我认为只是循环遍历函数列表并调用每个函数是如此明显,以至于问题必须更多。例如,给定这两个字符串操纵器:

def reverse(s):
    return s[::-1]

import random
def randomcase(s):
    return ''.join(random.choice((str.upper, str.lower))(c) for c in s)

manips = [reverse, randomcase]
s = "Now is the time for all good men to come to."

# boring loop through list of manips
for fn in manips:
    print fn(s)

# more interesting chain through list of manips
s_out = s
for fn in manips:
    s_out = fn(s_out)
print s_out

第一个循环打印:

.ot emoc ot nem doog lla rof emit eht si woN
NOW IS THe tIMe for aLL good meN TO COme To.

第二个将第一个函数的输出链接到下一个函数的输入,打印:

.oT EMoC OT NeM DOog lla RoF emit EHt SI won

第二种方法允许你用几个简单的函数组成更复杂的函数。