Pythonic仅当变量不是None时才进行if语句比较的方法

Pythonic仅当变量不是None时才进行if语句比较的方法,python,if-statement,Python,If Statement,如果阻塞,有没有更类似于蟒蛇的方法 def is_notification_needed(request: RiverPreference, gauge: Gauge) -> bool: """ Decides whether an email should be sent to the user or not based on their provided preferences. :param request: RiverPrefe

如果阻塞,有没有更类似于蟒蛇的方法

def is_notification_needed(request: RiverPreference, gauge: Gauge) -> bool:
    """
    Decides whether an email should be sent to the user or not based on their provided preferences.
    :param request: RiverPreference dataclass
    :param gauge: Gauge dataclass
    :returns: boolean
    """
    for preference in request:
        if preference.level and preference.trend and preference.level >= gauge.level and preference.trend == gauge.trend:
            return True
        elif preference.level and not preference.trend and preference.level >= gauge.level:
            return True
        elif preference.trend and not preference.level and preference.trend == gauge.level:
            return True
        return False

preference.trend
preference.level
在用户不想设置时默认为
None
。我希望只有在设置了仪表值后,才能对照仪表值检查这些值。

首先,最好明确地与
进行比较,而不是“滥用”无的布尔值。记住Python()中的“显式优于隐式”。就是

if preference.level is not None and ...
总比

if preference.level and ...
另一方面,通过执行以下操作,您可以利用
None
具有布尔
False
值这一事实:

if (preference.level or 0) >= gauge.level:
而不是:

if preference.level and preference.level >= gauge.level:
当然,您应该指定适当的值,而不是
0
(取决于
gauge.level
可以具有的值);这只是一个例子

使用
运算符为变量提供默认值,该变量可以是
(或
,或任何其他布尔假等价物),实际上在Python程序中非常常用,我将其称为“Pythonic”方式来表示


顺便说一句,你的
for
循环是没有意义的,因为你的循环体总是在第一次通过循环时返回。

我不知道这是否更像Pythonic,但我确实发现它更容易理解


需要def通知(请求:首选项,仪表:仪表)->bool:
"""
根据用户提供的首选项决定是否向用户发送电子邮件。
:param请求:RiverPreference数据类
:参数仪表:仪表数据类
:返回:布尔值
"""
首选项=请求[0]
如果preference.trend为无:
如果preference.level为无:
返回错误
返回首选项.trend>=仪表.level
elif preference.level为无:
返回首选项.trend==gauge.level
返回preference.level>=gauge.level和preference.trend==gauge.trend
这里的主要原则是尽早摆脱
None
情况,然后依赖于我们知道这些值已定义的事实,在后续代码中使用


如果由于其他原因,这些值也可能是错误的,则可能将
is None
更改为不太具体的值。

首先,python式的比较方法是
is not None
,如果您的值可能是错误的(
0
),这一点很重要

第二,你的缩进看起来不对劲,逻辑上有一个输入错误,但我认为你的目标是,如果满足任何偏好的所有条件,就返回True,否则返回False,通过检查否定,这会更简单

    for preference in request:
        if preference.level is not None and preference.level < gauge.level:
            continue
        if preference.trend is not None and preference.trend != gauge.trend:
            continue
        return True  # NB: treats all-None as a match
    return False
请求中的首选项:
如果preference.level不是None且preference.level
有许多逻辑上等效的方法可以做到这一点,但在这种情况下,我的偏好是反转逻辑,并尝试找出何时需要返回
False
,因为我们现在每个条件只有一个
,根据我的经验,这对代码的维护有很大的不同

(我假设
RiverPreference
作为一系列
preference
对象工作)

def是否需要通知(请求:首选项,仪表:仪表)->bool:
"""
根据用户提供的首选项决定是否向用户发送电子邮件。
:param请求:RiverPreference数据类
:参数仪表:仪表数据类
:返回:布尔值
"""
首选项=请求[0]
如果preference.level和preference.level

(如果
0
0.0
可以是仪表级别的有效值,您可能需要将
is None
添加到
首选项.级别
首选项.趋势
的检查中。)

结合您的条件,我不认为这有什么不妥之处。只需简单地使用布尔“and”和“or”运算符。在此之后,我删除了我的答案。您尽早消除None情况的逻辑比合并条件要好得多。
def is_notification_needed(request: RiverPreference, gauge: Gauge) -> bool:
    """
    Decides whether an email should be sent to the user or not based on their provided preferences.
    :param request: RiverPreference dataclass
    :param gauge: Gauge dataclass
    :returns: boolean
    """
    preference = request[0]
    if preference.level and preference.level < gauge.level:
         return False
    if preference.trend and preference.trend != gauge.level:
         return False
    return preference.level or preference.trend