True inconsistency in Python

S

Scott Chapman

There seems to be an inconsistency here:

Python 2.3.2 (#1, Oct 3 2003, 19:04:58)
[GCC 3.2 20020903 (Red Hat Linux 8.0 3.2-7)] on linux2
....
true ....
true
....
true ....
true
.... print "hello"
....False


Historically Python has allowed <> 0 to equal true in evaluations. Now
<> 0 still evaluates to true in evaluations. However it doesn't equal
True. They are not interchangable. (Same with empty lists, etc.)
Assuming the old behavior is desired, programmers need to be careful
not to compare a variable with True as in:

if var == True: # only works if var is 1
blah

' Must use:

if var: # works if var is not 0
blah

Is this inconsistency going to be resolved in the future?

How? (Will <>0 == True or will <>0 <> true or will it be resolved some
other way that I'm too opaque to see? :)

It seems that maybe Python should throw a warning (perhaps if a flag is
set) any time it bumps into code comparing a variable to True or False.
It's pretty subtle and would easily throw a newbie.

Of course, according to the above logic, if 1 == true and 2 == true,
then 1 == 2! Thankfully this doesn't work in Python. Python is magic.
I love the magic but it creates some interesting inconsistencies.

Scott
 
E

Erik Max Francis

Scott said:
Historically Python has allowed <> 0 to equal true in evaluations.
Now
<> 0 still evaluates to true in evaluations. However it doesn't equal
True. They are not interchangable. (Same with empty lists, etc.)

That's because the proper way to test for truth does not use the True
value at all. It is this:

if x:
...

not this:

if x == True:
...
 
B

Ben Finney

There seems to be an inconsistency here:

Yes. The inconsistency is in expecting all Boolean truths to be the
same value.

The object True will evaluate as a Boolean truth. The object False will
not evaluate as a Boolean truth. This doesn't mean that there are no
other values that will or won't evaluate as Boolean truth.

You many want to read the PEP that led to the creation of the 'bool'
type (and True and False objects):

<http://www.python.org/peps/pep-0285.html>

In short: Testing the Boolean truth of an expression is done with 'if',
not with value-comparison operators.
 
D

David C. Fox

Scott said:
if var == True: # only works if var is 1
blah

' Must use:

if var: # works if var is not 0
blah

Just because something isn't True doesn't mean it isn't true.

David
 
B

Ben Finney

The only thing that surprises me in all of this is the "if var:"
evaluating to true for numbers other than 1. That's new to me, I
would have expected an exception in that case.

Python has only recently gained a Boolean type ('bool').

<http://www.python.org/peps/pep-0285.html>

Before that, Boolean logic was done with integer values. Zero equated
to Boolean false, non-zero equated to Boolean true; and the default
Boolean true value was simply the integer 1.

This conflation of types is confusing, and (like many other languages)
Python has now "grown a Boolean type" to distinguish integer 0 and 1
from Boolean False and True. However, the previous behaviour is still
supported -- for how long, I don't know.
 
R

Ron Adam

Historically Python has allowed <> 0 to equal true in evaluations. Now
<> 0 still evaluates to true in evaluations. However it doesn't equal
True.
True

Seems to work for me. Am I missing something?

The only thing that surprises me in all of this is the "if var:"
evaluating to true for numbers other than 1. That's new to me, I
would have expected an exception in that case. But it still makes
since if I look at it as a shortcut for "if (var != 0):". This
only proves I'm still relatively new to Python I think.

_Ron Adam
 
R

Ron Adam

Python has only recently gained a Boolean type ('bool').

<http://www.python.org/peps/pep-0285.html>

Before that, Boolean logic was done with integer values. Zero equated
to Boolean false, non-zero equated to Boolean true; and the default
Boolean true value was simply the integer 1.

This conflation of types is confusing, and (like many other languages)
Python has now "grown a Boolean type" to distinguish integer 0 and 1
from Boolean False and True. However, the previous behaviour is still
supported -- for how long, I don't know.

That's good to know. I've always explicitly defined my bool values as
0 and 1 so it's never been a problem.

Thanks for the PEP link, it was informative.

_Ron Adam
 
M

Michael Geary

Ron Adam:
The only thing that surprises me in all of this is the
"if var:" evaluating to true for numbers other than 1.
That's new to me, I would have expected an
exception in that case. But it still makes since if I
look at it as a shortcut for "if (var != 0):". This only
proves I'm still relatively new to Python I think.

It's handy, and natural in many real life situations, to treat any nonzero
value as "true". For example:

Do you have any money in your wallet?

Do you have children?

I could ask how much money or how many children you have, but if I just ask
the yes-or-no question, you'll naturally answer "yes" for any nonzero value.

Of course, if you have children, you won't have money, but that's a separate
problem...

-Mike
 
B

Borcis

Scott said:
if var == True: # only works if var is 1
blah

' Must use:

if var: # works if var is not 0
blah

there's the equivalent, and more explicit :

if bool(var)==True : blah
 
D

Dang Griffith

That's because the proper way to test for truth does not use the True
value at all. It is this:

if x:
...

not this:

if x == True:
...
Sort of like (stretchy) saying that if these are both True:
"a snake is green"
"a pearl is white"
that they are the same as each other.
They are both true, yet unrelated. You can say:
if "a snake is green": print 1
if "a pearl is white": print 2
and the prints would happen, but if you said
if "a snake is green" == "a pearl is white": print 3
the print would not happen.

--dang
 
A

Alex Martelli

Borcis said:
there's the equivalent, and more explicit :

if bool(var)==True : blah

Why stop there? If adding one useless and redundant check is
better, surely having more will be merrier and merrier...:

if ( bool(var) == True) == True: doubleblah

oh wait, we should add ANOTHER level of uselessness...:

if (( bool(var) == True) == True) == True: tripleblah

oh wait...


"if var:" is the Pythonic way. You could argue that each
level of "== True" makes it ``more explicit'', but I just
consider them all equally silly in their utter redundancy.

[[ we TOLD Guido people would start on this absurd path, when
he added bool, True, and False, but he wouldn't listen...
]]


Alex
 
A

Alex Martelli

Ben Finney wrote:
...
This conflation of types is confusing, and (like many other languages)
Python has now "grown a Boolean type" to distinguish integer 0 and 1
from Boolean False and True. However, the previous behaviour is still
supported -- for how long, I don't know.

I've never heard of any plans (not even for the totally mythical
"Python 3000") to remove or even deprecate Python's extremely useful
and practical feature that:
-- any value can be used as a true-or-false condition,
-- zero numbers, empty containers, and user-coded objects defining
__nonzero__ (or else __len__) and returning 0 are taken as false,
-- all other values are taken as true.


Alex
 
E

Emile van Sebille

Ben Finney
You many want to read the PEP that led to the creation of the 'bool'
type (and True and False objects):

.... or vise versa

Emile van Sebille
(e-mail address removed)
 
A

Alex Martelli

Scott Chapman wrote:
...
It seems that maybe Python should throw a warning (perhaps if a flag is
set) any time it bumps into code comparing a variable to True or False.

It's a bit hard to do it just for variables, but doing it for _any_
comparison would _almost_ be reasonable -- testing if something
"== True" is hardly ever sensible. Unfortunately "a == b" CAN
be perfectly sensible and either or both of the variables MIGHT
just happen to be set to True.

However, this looks to me like a good suggestion for PyChecker
and the like, which should be able to catch and flag the actual
explicit use or the constant True in code involving == or != ...


Alex
 
G

Gerrit Holl

Alex Martelli wrote:
(about x vs. bool(x))
[[ we TOLD Guido people would start on this absurd path, when
he added bool, True, and False, but he wouldn't listen...
]]

What do double square brackets mean?

(btw, I _do_ use bool ocasionally: I implemented an anytrue() function
using sum([bool(i) for i in L]), is this wrong?)

Gerrit.
 
E

Erik Max Francis

Borcis said:
there's the equivalent, and more explicit :

if bool(var)==True : blah

The explicitness here does not gain you anything. In a truth context,
x, bool(x), and bool(x) == True are all precisely identical. There is
absolutely no value gained by writing bool(x) == True instead of just x.

--
Erik Max Francis && (e-mail address removed) && http://www.alcyone.com/max/
__ San Jose, CA, USA && 37 20 N 121 53 W && &tSftDotIotE
/ \
\__/ The golden rule is that there are no golden rules. -- George
Bernard Shaw
 
R

Ron Adam

Ron Adam:

It's handy, and natural in many real life situations, to treat any nonzero
value as "true". For example:

Do you have any money in your wallet?

Do you have children?

I could ask how much money or how many children you have, but if I just ask
the yes-or-no question, you'll naturally answer "yes" for any nonzero value.

Of course, if you have children, you won't have money, but that's a separate
problem...

-Mike

That makes since, Thanks for clarifying this.

I learned boolean logic as part of a computer tech degree back in
early 80's. Binary logic circuits use only 0 and 1. So it's the way
I think when dealing with bool type.

_Ron Adam
 
M

Michele Simionato

Gerrit Holl said:
(btw, I _do_ use bool ocasionally: I implemented an anytrue() function
using sum([bool(i) for i in L]), is this wrong?)

Gerrit.

It does not shortcut, i.e. it creates the full list. For the rest, it
is a matter of personal opinion if this idea is considered cool or
an abuse of sum. I personally, will propend for the latter, but since
we don't have yet an anytrue function in the library, for the moment it
can be tolered). Just my 0.02 E.

Michele
 
T

Terry Reedy

Ben Finney said:
This conflation of types is confusing,

but very useful
and (like many other languages)
Python has now "grown a Boolean type" to distinguish integer 0 and 1
from Boolean False and True. However, the previous behaviour is still
supported -- for how long, I don't know.

When bool was introduced, Guido promised that is would always remain a
subtype of int. Crippling usefulness in the name of mathematical
purity is not on the table.

Terry J. Reedy
 
T

Terry Reedy

Scott Chapman said:
There seems to be an inconsistency here:

In regard to logic, the current Python implementation acts just as
specified in the manaul, which is written as intended. This is the
only consistency relevant to Python.

In math, an inconsistent set of premises is one from which one can
derive both true and false. Python as delivered has no such
inconsistency in that sense either. bool(object) is either True or
False for every Python object except possibly for instances of a user
class with the appropriate special method mangled either by accident
or perverse intention.

In static math, x = x+1 is read as x == x+1, which is usually false.
But programming is not mathematics.

If you merely meant "Python is not consistent with my expectations"
then I suppose you are right. If that really bothers you, I suspect
you know the realistic remedy ;-).

Terry J. Reedy
 

Ask a Question

Want to reply to this thread or ask your own question?

You'll need to choose a username for the site, which only take a couple of moments. After that, you can post your question and our members will help you out.

Ask a Question

Members online

Forum statistics

Threads
473,780
Messages
2,569,611
Members
45,281
Latest member
Pedroaciny

Latest Threads

Top