【发布时间】:2012-08-05 16:12:25
【问题描述】:
是否有pythonic 方法来维护状态(例如,出于优化目的)而不完全面向对象?
为了更好地说明我的问题,这里有一个我在 JavaScript 中经常使用的模式示例:
var someFunc = (function () {
var foo = some_expensive_initialization_operation();
return someFunc (bar) {
// do something with foo and bar
}
}());
在外部,这只是一个和其他函数一样的函数,不需要初始化对象或类似的东西,但是闭包允许计算一次值,然后我基本上将其用作常量。
Python 中的一个例子是优化正则表达式时 - 使用 re.compile 并存储 match 和 search 操作的编译版本很有用。
我知道在 Python 中执行此操作的唯一方法是在模块范围内设置一个变量:
compiled_regex = compile_my_regex()
def try_match(m): # In reality I wouldn't wrap it as pointlessly as this
return compiled_regex.match(m)
或者通过创建一个类:
class MatcherContainer(object):
def __init__(self):
self.compiled_regex = compile_my_regex()
def try_match(self, m):
self.compiled_regex.match(m)
my_matcher = MatcherContainer()
前一种方法是临时的,函数和上面声明的变量之间的关联不是很清楚。它还稍微污染了模块的命名空间,我对此不太满意。
后一种方法看起来很冗长,而且在样板上有点沉重。
我能想到的解决这个问题的唯一另一种方法是将任何类似这样的函数分解到单独的文件(模块)中,然后只导入函数,这样一切都很干净。
更有经验的 Python 专家对如何处理这个问题有何建议?或者你只是不担心它并继续解决问题?
【问题讨论】:
-
我个人认为您的课程创建没有问题。冗长是好的。 "
Explicit is better than implicit." -
至少使该类的使用不那么冗长的一种方法是将
try_match重命名为__call__,这样您就可以(在构造之后)完全像使用函数一样使用它。但是,正如@glglgl 的回答一样,您的 javascript 代码实际上直接转换为 Python。 -
在您的第一个示例中调用 someFunc 是否正确?还是应该是函数定义?
-
调用是正确的 - 它执行外部函数,返回内部函数,这就是在外部范围内分配给
someFunc的内容。 -
@Cerales 抱歉,我仍在努力解决它。
return someFunc (bar) {}中的括号不是虚假的吗?另外如果someFunc(bar)是实际调用,会不会导致堆栈溢出?