UWPCE-PythonCert / PythonCertDevel

Development Repo for the Certificate Program
https://uwpce-pythoncert.github.io/PythonCertDevel/index.html
Other
7 stars 15 forks source link

Fix logic error in Booleans.rst (==,not is) #169

Closed hosungs closed 5 years ago

PythonCHB commented 5 years ago

Actually, it is generally recommended to use "is" rather than "==" for the singletons in Python, such as None, True and False.

(from PEP8: "Comparisons to singletons like None should always be done with is or is not, never the equality operators.")

If we wanted "truthiness" then you could simple say:

if x:
    ...

If you want to know that x is actually the False object, rather than anything that is considered False, then you use:

if x is False:
    ...

So I think we should keep it the way it is.

hosungs commented 5 years ago

@PythonCHB -- Didn't you want x is False to evaluate to True whenever bool(x) == False? For example, I thought you wanted x is False to evaluate True if x is bound to 0. But if you do x = 0 and see the value of x is False, it is False, not True (because the 0 object is certainly not the False singleton object, and is compares their ids, not the values.

I interpreted your example to mean the equivalence between x or y and if x is False: return y else: return x. However, they are not equivalent if x=0, which will give y for x or y, but x for if x is False: return y else: return x, because x is False is False even when x=0 (or any other value whose bool() is False). Please let me know if this is still unclear, or at least I think we need to fix the inconsistency.

Basically I want the following assertion to pass, but I get error (which I think is right), so I'm trying to fix that. Please advise if I misinterpreted your intention on these examples.

In [90]: def my_or1(x, y):
    ...:     return x or y
    ...:
    ...: def my_or2(x, y):
    ...:     if x is False:
    ...:         return y
    ...:     else:
    ...:         return x
    ...:

In [91]: assert my_or1(0, 1) == my_or2(0, 1)
--------------------------------------------------------------------------AssertionError                           Traceback (most recent call last)<ipython-input-91-8c866b1b74a5> in <module>()
----> 1 assert my_or1(0, 1) == my_or2(0, 1)

AssertionError:

In [92]:
PythonCHB commented 5 years ago

I’m on a phone, so need to look again in a broader context, but as a rule, we want examples to be “pythonic”, which in this case means:

If X is False

If you are checking for the False object.

And:

If X:

If checking for “truthiness”

If we want to be more explicit for an example, then:

If bool(X):

Or even more explicit:

If bool(X) is False:

So in your example, in my_or2, I’d do:

If bool(x) is False: return y

-CHB

PythonCHB commented 5 years ago

OK I now see where the original example you edited is used — yes, that should be updated, but not with ==, but rather with bool().

hosungs commented 5 years ago

Absolutely. In fact, I wouldn't even use if bool(x) is False:, as my original thought was just to use if not x:. Only reason I fixed this by changing is with == is just to point out the is vs == subtlety with this example, and I expected that you'd propose a better/pythonic fix. Thanks!

PythonCHB commented 5 years ago

OK -- I've updated this in master and rendered it -- see what you think.

Thanks for bringing this up -- that was confusing!

hosungs commented 5 years ago

Just looked at the new rendering, and it looks good. Thanks!