# None und True/False

n = None

if not None:
    print('bool(None) ist immer False')

print('' == None) # False
print(0 == None)  # False
print()

# Identität
print('' is None)        # False
print(0 is None)         # False
print(id(0), id(None))   # id() liefert die Speicheradresse eines Objekts
print(id(0) == id(None)) # False
print()

# True / False
print(0 == False)        # True
print(0 != False)        # False
print(0 is True)         # False
print(0 is not True)     # True
print(not 0 is True)     # True
print()

print(not 1 is True)     # True ("is" bindet stärker als "not")
print(not (1 is True))   # True
print((not 1) is True)   # False
print((not 0) is True)   # True
print()

# mit True/False kann man rechnen
print(int(True), int(False)) # 1 0
print(0 + True)              # 1
print(0 + False)             # 0
print(True + False)          # 1
print()

# bei Vergleichen mit Zahlen werden True/False nach 1/0 konvertiert
print(1 == True)  # True, da 1 == int(True)
print(0 == False) # True, da 0 == int(False)
print(1 is True)  # False, da 1 und True verschiedene Objekte sind
print(0 is False) # False, da 0 und False verschiedene Objekte sind
print()

# Boolesche Ausdrücke
#
# x or y  ==> wenn x falsch, dann y, sonst x
# x and y ==> wenn x falsch, dann x, sonst y
# not x   ==> wenn x falsch, dann True, sonst False
#
# Operatorpräzedenz:
#   1. not
#   2. and
#   3. or
#
# short-circuit evaluation: sobald das Ergebnis feststeht, endet die Auswertung
# des Booleschen Ausdrucks

print(4 and 0 or 5)     # 5 ("and" bindet stärker als "or")
print(4 or 0 and 5)     # 4
print((0 or 1) and 5)   # 5
print(0 or None and 5)  # None
print(0 or True and 5)  # 5
print(0 or False and 5) # False
print(0 and 1 / 0)      # 0 (kein ZeroDivisionError, da 1 / 0 nicht ausgewertet wird)
print()

if 0 and True:
    # mit "0 and" kann man Code-Teile deaktivieren
    print('nie erreicht')

if 1 or False:
    # und mit "1 or" stets aktivieren
    print('stets erreicht')

print(not 5)            # False
print(not not 5)        # True
print(4 or 9)           # 4
print(not not (4 or 9)) # True
