【问题标题】:Is there a Python library (or pattern) like Ruby's andand?是否有像 Ruby 的 andand 这样的 Python 库(或模式)?
【发布时间】:2011-12-15 11:15:17
【问题描述】:

例如,我有一个对象x,它可能是None 或浮点数的字符串表示。我想做以下事情:

do_stuff_with(float(x) if x else None)

除了不必输入x 两次,如Ruby 的andand 库:

require 'andand'
do_stuff_with(x.andand.to_f)

【问题讨论】:

    标签: python ruby null andand


    【解决方案1】:

    我们没有其中之一,但不难推出您自己的:

    def andand(x, func):
        return func(x) if x else None
    
    >>> x = '10.25'
    >>> andand(x, float)
    10.25
    >>> x = None
    >>> andand(x, float) is None
    True
    

    【讨论】:

    • 模仿 Ruby 的 andand:return (func(x) if (x is not None) else None)。并且可能会发送可选的额外参数:def andand(x, func, *args, **kwargs)
    • 我喜欢,有tokland的建议,简洁有力。
    【解决方案2】:

    从 Raymond 的想法开始,这里有一个制造这种条件包装器的工厂。既然可以让 Python 为您编写它们,为什么还要自己编写它们呢?

    def makeandand(func):
        return lambda x: func(x) if x else None
    
    andandfloat = makeandand(float)
    
    andandfloat('10.25')
    >>> 10.25
    
    andandfloat('')
    >>> None
    

    andand 不完全是 Pythonic,但我不知道有一个更好的名字。可能是trap,因为您捕获了无效值。

    值得注意的是,一个常见的 Python 习语是继续尝试做你需要做的事情,并在出现异常时处理它们。这被称为 EAFP,来自格言“请求宽恕比许可更容易”。所以也许一种更 Pythonic 的写法是:

    def maketrap(func, *exceptions):
        def trap(x):
            try:
                return func(x)
            except exceptions or (Exception,):
                return None
        return andand
    
    trapfloat = maketrap(float)
    
    # optionally specify the exceptions to convert to a None return
    # (default is to catch anything but you may want to allow some through)
    trapfloat = maketrap(float, ValueError)
    trapfloat = maketrap(float, ValueError, TypeError)
    
    # if you don't want to store it (i.e. you only need it once or twice)...
    maketrap(float)(x)    # ... just call it immediately
    

    在您的用例中,我认为这种方法是一个胜利:它透明地处理可以转换为float任何东西,并且如果是假的,则做“正确的事情”-但是-convertible-to-float值(如0)传入。

    【讨论】:

    • 这个解决方案很有创意,在某些用例中绝对有用。但我不想为我使用的每一种方法都创建包装器,特别是如果我只使用一次或两次。
    • @Andres:对于那些一次性用例,您可以立即调用它:maketrap(float)("2.5") 等。
    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 2018-05-28
    • 2011-03-24
    • 1970-01-01
    • 2010-10-09
    • 2011-04-03
    • 1970-01-01
    • 2017-07-24
    相关资源
    最近更新 更多