Python 3和 - 或vs if-else

Mar*_*nen 4 python if-statement operators logical-operators python-3.x

以下是否有任何区别?

print(x if x else 'no x available')
# compared to:
print(x and x or 'no x available')
Run Code Online (Sandbox Code Playgroud)

Iva*_*ass 10

两条线都相同:

print(x or 'no x available')
Run Code Online (Sandbox Code Playgroud)

关于第二种选择:始终记住,根据运算符优先级and首先进行计算x and x,所以首先计算,这是完全没用的 - 它等于x


luk*_*k32 5

运行这个:

import dis
def f1():
  print(x if x else 'no x available')
def f2():
  print(x and x or 'no x available')
def f3():
  print(x or 'no x available')
dis.dis(f1)
dis.dis(f2)
dis.dis(f3)
Run Code Online (Sandbox Code Playgroud)

我们得到,对于f1

  4           0 LOAD_GLOBAL              0 (x)
              3 POP_JUMP_IF_FALSE       12
              6 LOAD_GLOBAL              0 (x)
              9 JUMP_FORWARD             3 (to 15)
        >>   12 LOAD_CONST               1 ('no x available')
        >>   15 PRINT_ITEM          
             16 PRINT_NEWLINE       
             17 LOAD_CONST               0 (None)
             20 RETURN_VALUE        
Run Code Online (Sandbox Code Playgroud)

对于f2

  7           0 LOAD_GLOBAL              0 (x)
              3 POP_JUMP_IF_FALSE       12
              6 LOAD_GLOBAL              0 (x)
              9 JUMP_IF_TRUE_OR_POP     15
        >>   12 LOAD_CONST               1 ('no x available')
        >>   15 PRINT_ITEM          
             16 PRINT_NEWLINE       
             17 LOAD_CONST               0 (None)
             20 RETURN_VALUE        
Run Code Online (Sandbox Code Playgroud)

对于f3从@Klass伊万采取:

 10           0 LOAD_GLOBAL              0 (x)
              3 JUMP_IF_TRUE_OR_POP      9
              6 LOAD_CONST               1 ('no x available')
        >>    9 PRINT_ITEM          
             10 PRINT_NEWLINE       
             11 LOAD_CONST               0 (None)
             14 RETURN_VALUE        
Run Code Online (Sandbox Code Playgroud)

所以f1f2不一样。正如克拉斯所提到的,它们确实有不同的逻辑。f3f1版本也不同,即使在逻辑上它们应该是等效的,但f3省去了一些操作。


Dun*_*can 5

在实践中它们是相同的;理论上它们是不同的,但仅当该__bool__方法有副作用时:

>>> class Weird:
    state = False
    def __bool__(self):
        self.state = not self.state
        return self.state


>>> x = Weird(); print(x if x else 'no x available')
<__main__.Weird object at 0x0000000003513160>
>>> x = Weird(); print(x and x or 'no x available')
no x available
Run Code Online (Sandbox Code Playgroud)

如果您遇到这个理论案例,您需要担心的问题更严重。

另请注意:

>>> x = Weird(); print(x or 'no x available')
<__main__.Weird object at 0x00000000035071D0>
Run Code Online (Sandbox Code Playgroud)

所以 Klass Ivan 的回答在技术上是错误的。

最重要的是,使用该if表达式,因为它可以更清楚地表达您的意思。