1

我想编写一种 CPS 代码更高的功能。他们应该获取一个功能代码,将其封装在对象中,并添加组合这些对象的方法。

像这样的东西:

myFunction=MyFunction(
  a = b+c
  print(c)
  return a)

但是对于匿名函数,只有一个 Python 表达式——lambda 语句。它不太适合。

Python 是一门强大的语言,它有不同的表达方式:装饰器、eval 等……有没有像上面提到的例子那样编写匿名函数的好方法?

另一种方法是使用特殊函数(如 monadic bind 和 return)扩展 lambda 表达式,以及用于编写单行复杂表达式的其他高阶函数。

主要目的是创建自定义抛出控制表达式。

class TimeoutExpression:
  def __init__(self,name,function,timeout):
    ...
  def eval(self):
    """ eval functions, print result and error message
      if functions failed to calculate in time """
    ...
  def andThen(self,otherExpression):
    """ create complex sequential expression"
    ...
  def __call__(self):
    ...

它的使用方式如下:

TimeoutExpression( time consuming calculation ).andThen(
  file object access).andThen(
    other timer consuming calcualtion )

创建自定义控制流结构的最佳 python 惯用方式是什么?

我已经阅读了讨论:如何在 Python 中创建匿名函数而不用洗礼? 提到了几个采用相同方法的决定:从三重引号字符串生成函数。虽然行为完全正确,但似乎很麻烦。它是目前设计的最佳方法吗?

更新

有人告诉我没有问题,python 允许你在任何上下文中使用def 。我假设我的 python 经验欺骗了我,并尝试按照建议在任何范围内使用def 。 我有一个错误。在任何情况下我应该如何准确地放置def ?

def compose(f):
    return lambda k: lambda x: f(k(x))

test = compose( def sqr(x) :
                print ("sqr "+str(x))
                return x*x
                return sqr) ( def x2(x):
                              print("x2 "+str(x))
                              return x*2
                              return x2 )

错误:

Traceback (most recent call last):
  File "<input>", line 1, in <module>
  File "anonFunction.py", line 4
    test = compose( def sqr(x) :
                  ^
SyntaxError: invalid syntax
4

3 回答 3

3

使用 lambda 的 wrt Python 没有任何优势。Lambda 和 Anonymous 函数一般用于简单函数,如果需要更复杂的多行函数,编写命名函数更易读。

由于函数是第一类对象,您可以简单地定义它,将其分配给变量并使用它并传递它。除非您需要一个可以选择 lambda 的一次性简单函数,否则命名函数是有利的。尽管如此,在从未完全 Pythonic 中使用 lambda。

回到你的例子,

myFunction=MyFunction(
  a = b+c
  print(c)
  return a)

在 Python 中,将其编写为

def MyFunction:
    a =b + c
    print c
    return a

然后将它传递给你的代码,就像MyFunctionPythonic 一样。我在 Javascripts 中看到了 Callbacks 以匿名方式编写的代码。但是每种语言都有自己的哲学,而 Python 的哲学是可读性。

---可读性很重要。

于 2012-04-19T19:14:04.120 回答
1

我有一个技巧——这确实是唯一合适的术语——使用嵌套函数,它提供了多行 lambda 可能提供的那种功能。你可以在这里查看我的 GitHub 存储库。

基本上它允许您执行以下操作:

fibonacci = f('result = t(a-1)+t(a-2) if a>2 else 1; return result')
fibonacci(6) #Output: 8

或者更多的是匿名函数:

cube = f('result = a**3; return result')(4)
print(cube) #Output: 64

这种黑客攻击显然有局限性。例如,我还没有想出一种方法来实现更复杂的缩进结构,比如ifor while,但同样,这是一个非常便宜的 hack。

于 2012-08-03T18:12:15.240 回答
1

在 Python 中,使用lambda关键字,您只能创建一个计算单个表达式并返回结果的函数对象。要使用语句或多行创建函数,您必须使用def关键字,该关键字需要名称。

限制的原因lambda主要是基于 Python 将行尾视为一件重要的事情:

Python 中没有多行 Lambda:为什么不呢?

然而,名字并不重要。您可以制定一个约定,即您的每个“匿名”函数都将使用名称anon或其他内容进行定义。如果你真的在乎,你可以抹去名字的所有痕迹:

y = 5
def anon(x):
    return x + y  # note "closure" over the current value of y

myFunction = anon

# if you really care, you can erase all evidence of name "anon"
anon.__name__ = ''  # wipe the record of original name "anon"
del(anon)  # unbind the name "anon"

因此,对于函数式编程,Python 可以创建一流的函数对象,传递它们等等。Python 不能做的一件事是创建一个从不具有名称的复杂函数对象,但实际上没有理由说这很重要。

于 2012-04-19T19:41:07.133 回答