Why Is '' > 0 True in Python 2

Is False == 0 and True == 1 an implementation detail or is it guaranteed by the language?

In Python 2.x this is not guaranteed as it is possible for True and False to be reassigned. However, even if this happens, boolean True and boolean False are still properly returned for comparisons.

In Python 3.x True and False are keywords and will always be equal to 1 and 0.

Under normal circumstances in Python 2, and always in Python 3:

False object is of type bool which is a subclass of int:

    object
|
int
|
bool

It is the only reason why in your example, ['zero', 'one'][False] does work. It would not work with an object which is not a subclass of integer, because list indexing only works with integers, or objects that define a __index__ method (thanks mark-dickinson).

Edit:

It is true of the current python version, and of that of Python 3. The docs for python 2 and the docs for Python 3 both say:

There are two types of integers: [...] Integers (int) [...] Booleans (bool)

and in the boolean subsection:

Booleans: These represent the truth values False and True [...] Boolean values behave like the values 0 and 1, respectively, in almost all contexts, the exception being that when converted to a string, the strings "False" or "True" are returned, respectively.

There is also, for Python 2:

In numeric contexts (for example when used as the argument to an arithmetic operator), they [False and True] behave like the integers 0 and 1, respectively.

So booleans are explicitly considered as integers in Python 2 and 3.

So you're safe until Python 4 comes along. ;-)

Why does 1 == True but 2 != True in Python?

Because Boolean in Python is a subtype of integers. From the documentation:

Boolean values are the two constant objects False and True. They are used to represent truth values (although other values can also be considered false or true). In numeric contexts (for example when used as the argument to an arithmetic operator), they behave like the integers 0 and 1, respectively. The built-in function bool() can be used to cast any value to a Boolean, if the value can be interpreted as a truth value (see section Truth Value Testing above).

http://docs.python.org/library/stdtypes.html#boolean-values

Why is `True and ~True` -2?

True has a value of 1 in Python. Bit-inverting (~) a binary 1 (...0001) gives you ...1110. Since negative integers are represented by two's compliment, that's a value of -2.

Logical and returns its left operand if it's false, the right operand otherwise. (True is never false, obviously.)

Bitwise &, on the other hand, works on the individual bits. ...0001 & ...1110 have no 1 bits in the same position so they're all zeros in the result.



I was just surprised that a numpy array with dtype=bool acts differently with literal bool

Each Python type can implement an operator's methods with special method names. (Like .__invert__() for ~). But and, or, and not don't have these hooks, so often &, |, and ~ are used instead. For ints the implementation is bitwise, but other types can interpret operators however they want.

Note that bool is a subclass of int in Python, so it has the same operators as int. But you were operating on a numpy.ndarray, not on its individual components, so Python uses the ndarray implementation of the operators, which are not the same as bool when dtype=bool.

Is 0 False and all other integer values True?

0 and 1 are analogous to booleans False and True respectively.

You can test it like:

>>> bool(0)
False
>>> bool(1)
True

In fact every number that is not zero, is truthy:

>>> bool(3)
True

which again confirms that a not on number (non-zero) yields False (not True = False):

>>> not True
False
>>> not 3
False

Why in Python 1.0 == 1 True; -2.0 == -2 True and etc.?

isinstance(x, (int, long))

isinstance tests whether the first argument is an instance of the type or types specified by the second argument. We specify (int, long) to handle cases where Python automatically switches to longs to represent very large numbers, but you can use int if you're sure you want to exclude longs. See the docs for more details.

As for why 1.0 == 1, it's because 1.0 and 1 represent the same number. Python doesn't require that two objects have the same type for them to be considered equal.

Python evaluates 0 as False

In Python, bool is a subclass of int, and False has the value 0; even if values weren't implicitly cast to bool in an if statement (which they are), False == 0 is true.

Python: False vs 0

In Python,

  • The is operator tests for identity (False is False, 0 is not False).

  • The == operator which tests for logical equality (and thus 0 == False).

Technically neither of these is exactly equivalent to PHP's ===, which compares logical equality and type - in Python, that'd be a == b and type(a) is type(b).

Some other differences between is and ==:

Mutable type literals

  • {} == {}, but {} is not {} (and the same holds true for lists and other mutable types)
  • However, if a = {}, then a is a (because in this case it's a reference to the same instance)

Strings

  • "a"*255 is not "a"*255", but "a"*20 is "a"*20 in most implementations, due to how Python handles string interning. This behavior isn't guaranteed, though, and you probably shouldn't be using is in this case. "a"*255 == "a"*255 and is almost always the right comparison to use.

Numbers

  • 12345 is 12345 but 12345 is not 12345 + 1 - 1 in most implementations, similarly. You pretty much always want to use equality for these cases.


Related Topics



Leave a reply



Submit