Python:分钟(无,x)

Posted

技术标签:

【中文标题】Python:分钟(无,x)【英文标题】:Python: min(None, x) 【发布时间】:2011-09-09 10:30:50 【问题描述】:

我想执行以下操作:

a=max(a,3)
b=min(b,3)

但有时ab 可能是None。 我很高兴地发现在max 的情况下效果很好,给出了我需要的结果3,但是如果bNoneb 仍然是None...

任何人都可以想到一个优雅的小技巧,让min 返回数字,以防万一没有参数之一?

【问题讨论】:

它没有做正确的事情。它恰好在两种情况之一中给出了您期望的结果,因为NoneTypeint 之间的无意义比较返回一个固定值,而不管整数值如何。在 Python 3 中,当您执行类似操作(比较没有有意义的排序的类型)时,您会得到一个 TypeError 似乎是 Python 中的一个不一致之处,最重要的是。 ***.com/questions/2214194/… 如果您可以将 None 替换为默认的 int 值(如 0),您可以执行以下操作:max(a,3,key=lambda x: x or 0) 【参考方案1】:

为什么不创建一个没有 None 值的生成器?它更简单、更干净。

>>> l=[None ,3]
>>> min(i for i in l if i is not None)
3

【讨论】:

不需要列表理解。仍然 +1(提前 - 认真,请删除括号),这是一个干净简单的解决方案。 谢谢,没有大括号,Python 会像生成器表达式一样解释它吗? 是的。如果genexpr 是函数调用的唯一参数,则生成器表达式周围的括号是可选的。 这样的解决方案的一个潜在问题是它适用于列出的示例,但如果您有一个带有[None, None] 的列表,min() 函数将失败,因为您没有给出它一个有效的论点。 @KevinLondon,根据您想要的行为将 min 的默认值指定为 0 或 None。 min((x for x in [None,None] if x is not None), default=None)【参考方案2】:

我对 Python 3(3.4 及更高版本)的解决方案:

min((x for x in lst if x is not None), default=None)
max((x for x in lst if x is not None), default=None)

【讨论】:

【参考方案3】:

Python 3 的解决方案

代码

#变量 lst 是你的序列

min(filter(lambda x: x is not None, lst)) if any(lst) else None

示例:

In [3]: lst = [None, 1, None]

In [4]: min(filter(lambda x: x is not None, lst)) if any(lst) else None
Out[4]: 1

In [5]: lst = [-4, None, 11]

In [6]: min(filter(lambda x: x is not None, lst)) if any(lst) else None
Out[6]: -4

In [7]: lst = [0, 7, -79]

In [8]: min(filter(lambda x: x is not None, lst)) if any(lst) else None
Out[8]: -79

In [9]: lst = [None, None, None]

In [10]: min(filter(lambda x: x is not None, lst)) if any(lst) else None

In [11]: print(min(filter(lambda x: x is not None, lst)) if any(lst) else None)
None

注意事项:

按顺序呈现为数字和无。如果所有值都是 None min() 引发异常

ValueError: min() arg 是一个空序列

这段代码完全解决了这个问题

优点:

    如果没有按顺序出现,则工作 使用 Python 3 max() 也可以使用

缺点

    列表中需要多个非零变量。即 [0,None] 失败。 需要一个变量(例如lst)或需要复制序列

【讨论】:

这也适用于 Python 2.7。由于它还解决了其他解决方案的 min(None) 问题,它得到了我的 +1 一个不能处理的边界情况是lst 可能只包含 0 和 None 值。您希望它返回 0,但它会返回 None。 很好的答案和例子!【参考方案4】:

这是一个内联装饰器,您可以使用它来过滤掉可能传递给函数的 None 值:

noNones = lambda fn : lambda *args : fn(a for a in args if a is not None)
print noNones(min)(None, 3)
print noNones(max)(None, 3)

打印:

3
3

【讨论】:

【参考方案5】:
def max_none(a, b):
    if a is None:
        a = float('-inf')
    if b is None:
        b = float('-inf')
    return max(a, b)

def min_none(a, b):
    if a is None:
        a = float('inf')
    if b is None:
        b = float('inf')
    return min(a, b)

max_none(None, 3)
max_none(3, None)
min_none(None, 3)
min_none(3, None)

【讨论】:

请注意,这仅在默认值为 0 时有效。传递 0 而不是 None 仍会触发传递默认值,但不会更改值,因为默认值为 0(和 0 == 0.0 == 0j)。 OP 说 max 不是问题。如果 b 为负数会怎样?【参考方案6】:

您可以使用内联 if 和 infinity 作为默认值,因为这适用于任何值:

a = max(a if a is not None else float('-inf'), 3)
b = min(b if b is not None else float('inf'), 3)

【讨论】:

好的,那我就说得更清楚一点 那么这有时会通过True ;)【参考方案7】:
a=max(a,3) if a is not None else 3
b=min(b,3) if b is not None else 3

【讨论】:

我总是尽量避免否定。所以我更喜欢b = 3 if b is None else min(b, 3)【参考方案8】:

@utdemir 的回答非常适合提供的示例,但在某些情况下会引发错误。

出现的一个问题是,如果您的列表仅包含 None 值。如果您向min() 提供一个空序列,则会引发错误:

>>> mylist = [None, None]
>>> min(value for value in mylist if value)
Traceback (most recent call last):
  File "<stdin>", line 1, in <module>
ValueError: min() arg is an empty sequence

因此,这个 sn-p 可以防止错误:

def find_minimum(minimums):
    potential_mins = (value for value in minimums if value is not None)
    if potential_mins:
        return min(potential_mins)

【讨论】:

【参考方案9】:

我相信最干净的方法是使用过滤器内置功能

a = max(filter(None, [a, 3]))
b = min(filter(None, [b, 3]))

【讨论】:

这会过滤掉零。

以上是关于Python:分钟(无,x)的主要内容,如果未能解决你的问题,请参考以下文章

从现在开始在 python 中的 X 分钟 [重复]

X分钟速成Y (其中Y=Python)

Python速查表在x分钟内入门Python (干货分享)

python20分钟入门

利用python实现每x分钟截屏一次存放到指定文件夹

如何使用 python-xmpp(和 gtalk)每 x 分钟向收件人发送一条消息?