如果不 (变量) 和 如果 (变量) == false 有什么区别?

3

我正在学习 Python,刚开始学习布尔条件语句。

但是我对于“如果不”的具体主题感到非常困惑。请问有人能够解释一下以下两种情况之间的区别:

x = False

if not x:
   print("hello")

if x == False:
   print("hello")

在Python编译器上测试此代码时,我会收到两次“hello”的输出。可以假设这意味着它们在计算机中有相同的含义。
请问为什么要使用其中一种方法而不是另一种方法?

3
请重复介绍导览中的 on topichow to ask 的内容。你正在要求关于已经在其他地方得到详细涵盖的主题的个人教程。请参阅How much research?,了解所需的研究工作量。 - Prune
1
此外,了解bool(x)__bool__ - Mad Physicist
1
我认为这个问题是相关的。这两种形式之间的区别并不明显。在高度类型化的语言中,优化编译器可能会将这两个语句降级为相同的代码位,但Python不会。而且这对于语言来说非常基本。 - tdelaney
@Prune,我正在CodeAcademy学习if not语句,但这个主题仍然让我感到困惑,我无法理解它。我在StackOverflow上寻找答案,但没有人能回答我特别关心的问题。如果我的问题让你不快,我很抱歉,下次提问时我会注意这些术语。 - WillPak_Alt
1
不,这并不是无关的。请参考我提供的发布指南。 - Prune
显示剩余2条评论
4个回答

4

这得看情况™。Python 不知道其运算符应该做什么,它会在对象上调用魔术方法并让它们自己决定。我们可以通过一个简单的测试来证明这一点。

class Foo:
  
    """Demonstrates the difference between a boolean and equality test
    by overriding the operations that implement them."""
    def __bool__(self):
        print("bool")
        return True

    def __eq__(self, other):
        print("eq", repr(other))
        return True

x = Foo()

print("This is a boolean operation without an additional parameter")
if not x:
    print("one")

print("This is an equality operation with a parameter")
if x == False:
    print("two")

生产

This is a boolean operation without an additional parameter
bool
This is an equality operation with a parameter
eq False
two

在第一个情况下,Python通过调用__bool__进行布尔测试,在第二个情况下,通过调用__eq__进行等式测试。这意味着什么取决于类。通常很明显,但像pandas这样的东西可能会变得棘手。
通常not xx == False更快,因为__eq__运算符通常在确定之前会执行第二次布尔比较。在您的情况下,当x = False时,您正在处理用C编写的内置类,其两个操作将类似。但是,x == False比较需要对另一侧进行类型检查,因此会稍微慢一些。

我不太确定你写的代码在if语句之前具体意味着什么,但是对于“速度”解释方面,确实帮了很大忙。非常感谢。 :D - WillPak_Alt
不确定额外的注释是否有帮助。Foo是一个类,它重写了你的测试中使用的魔术方法。这变得更加复杂,因为Python还为没有给定魔术方法的类制定了回退规则。默认的object对象实现了默认的魔术方法,大多数派生对象实际上并没有重新实现它们自己。 - tdelaney

3

这里已经有几个很好的答案了,但没有讨论Python中“真值”和“假值”表达式的一般概念。

在Python中,“真值”表达式是指转换为bool时返回True的表达式,“假值”表达式是指转换为bool时返回False的表达式。(参考:Trey Hunner的正则表达式教程;我与Hunner无关,我只是喜欢他的教程。)

假值:

重要的是,00.0[]NoneFalse都是假值。

当在if语句中使用时,它们将不通过测试,在if not语句中它们将通过测试。

真值:

非零数字、非空列表、许多对象(但请参阅@tdelaney的答案以获取更多详细信息),以及True都是真值,因此它们通过if测试并失败if not测试。

相等性测试

当您使用相等性测试时,您不是在询问表达式的真实性,而是在询问它是否等于您提供的其他事物,这比一般的真实性或虚假性要严格得多。

编辑:附加参考资料

以下是有关Python中“Truthy”和“Falsy”值的更多参考资料:


2

在一个情况下,你正在检查是否等于值"False",而在另一个情况下,你正在对变量执行布尔测试。在Python中,有几个变量可以通过 "if not x" 测试,但只有 x = False 可以通过 "if x == False" 测试。

请参考以下示例代码:

x = [] # an empty list

if not x: print("Here!")
# x passes this test

if x == False: print("There!")
# x doesn't pass this test

当我输入这段代码时,它会打印出“Here!”两次。虽然这很令人困惑,但它是如何将0识别为False的呢?0只是一个数字。 - WillPak_Alt
错误是我的,这在Python中非常特殊(我完全忘记了哈哈),但对于编译器来说,0和False是相同的东西。现在尝试运行它,我已经修复了它。 - Luiz F. Bianchi
作为一般规则,布尔测试(if / if not)比与True或False进行比较更加有效。 - Luiz F. Bianchi
还有一件事,有一本来自O'Reilly出版社的书叫做《学习Python》,它非常详细地讲解了这些更为概念性的内容。我真的很推荐它。 - Luiz F. Bianchi

0
尝试使用x = None:此时not x为True,而x == False为False。与x = False不同,此时两者都为True。not语句还可以处理空值。

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接