What is up with "=="?

Q

Quentin Crain

Hello All!

Could someone explain (links are good too!) why:
Traceback (most recent call last):
File "<stdin>", line 1, in ?
TypeError: unsupported operand types for +: 'int' and
'str'0

1 Whos __eq__ or __cmp__ is being called: String's or
Int's?
2 Why IS comparison supported across types?
3 The exception + gives makes it sound like there is
a built-in function + that does not like taking an
'int' and a 'string'. Read this way, the built-in ==
does accept 'int' and 'string'.

Anyway, I have spent a good 10-15 mins googling for
things like 'python subclass int' and have not found
anything useful. (PEP's 252 and 253 did not help me --
perhaps I misread them?)

What am I missing!

Quentin



=====
-- Quentin Crain

------------------------------------------------
I care desperately about what I do.
Do I know what product I'm selling? No.
Do I know what I'm doing today? No.
But I'm here and I'm gonna give it my best shot.
-- Hansel

__________________________________
Do you Yahoo!?
The New Yahoo! Shopping - with improved product search
http://shopping.yahoo.com
 
E

Erik Max Francis

Quentin said:
1 Whos __eq__ or __cmp__ is being called: String's or
Int's?
2 Why IS comparison supported across types?
3 The exception + gives makes it sound like there is
a built-in function + that does not like taking an
'int' and a 'string'. Read this way, the built-in ==
does accept 'int' and 'string'.

It's really a judgement call. It's certainly possible to set up an
equality operator which respects type, but in a dynamic language like
Python, you'll often find yourself comparing objects of different types
for equality. This can get inconvenient, since this means that this
comparisons would raise TypeErrors when all you really care about is
whether or not they're equal or not. Two objects of different types are
obviously unequal (unless __eq__ is deliberately overridden, etc.,
etc.), so it makes sense to simply have == and != not raise TypeErrors.

In fact, it's so common, that if your standard equality operator _does_
raise TypeErrors, you're almost guaranteeing you need another builtin
equality operator which does _not_ respect type. So now you have two
equality operators, which can be confusing -- there's
test-equality-and-raise-if-the-types-are-different and
test-equality-and-treat-different-types-as-simply-unequal. This isn't
necessarily the end of the world, but it's inconvenient. (For the
record, I used this approach -- two equality operators, `eq' and `seq'
-- so I'm not opposed to it on general principle.)

Plus the dynamicism of Python itself enters into it. I can easily come
up with custom classes, whether actually derived from numeric types or
not, which I _do_ want to test equal to existing types. Now it's
looking much more like it would be advantageous for equality to simply
not raise an error on different types and just say, "Nope, they're not
equal."
 
A

Andrew Dalke

Quentin Crain:
1 Whos __eq__ or __cmp__ is being called: String's or
Int's?

I suspect the int. Does it make a difference?
2 Why IS comparison supported across types?

Historical implementation reasons. There used to be no way for
a comparison to raise an exception. That's changed, but old code
which depended on this hasn't.
3 The exception + gives makes it sound like there is
a built-in function + that does not like taking an
'int' and a 'string'. Read this way, the built-in ==
does accept 'int' and 'string'.

That's an implementation issue I don't know enough about.
Ie, it may be implemented as that even if the implementation
acts identical to one where the tests are done as method of
the type.

Andrew
(e-mail address removed)
 
T

Terry Reedy

Quentin Crain said:
2 Why IS comparison supported across types?

There are only two simple rules: only compare within types; allow all
compares. If two things are not equal, why not say so?

Besides history, consider the following intentional feature:1 #True in 2.3

One could also import a rational or fixed-point number module and if
their classes have the needed special method, add them to the list.

Also consider this:0 # False in 2.3

Would you really want to get an exception rather than False?

Terry J. Reedy
 
B

Bengt Richter

It's really a judgement call. It's certainly possible to set up an
equality operator which respects type, but in a dynamic language like
Python, you'll often find yourself comparing objects of different types
for equality. This can get inconvenient, since this means that this
comparisons would raise TypeErrors when all you really care about is
whether or not they're equal or not. Two objects of different types are
obviously unequal (unless __eq__ is deliberately overridden, etc.,
etc.), so it makes sense to simply have == and != not raise TypeErrors.

In fact, it's so common, that if your standard equality operator _does_
raise TypeErrors, you're almost guaranteeing you need another builtin
equality operator which does _not_ respect type. So now you have two
equality operators, which can be confusing -- there's
test-equality-and-raise-if-the-types-are-different and
test-equality-and-treat-different-types-as-simply-unequal. This isn't
necessarily the end of the world, but it's inconvenient. (For the
record, I used this approach -- two equality operators, `eq' and `seq'
-- so I'm not opposed to it on general principle.)

Plus the dynamicism of Python itself enters into it. I can easily come
up with custom classes, whether actually derived from numeric types or
not, which I _do_ want to test equal to existing types. Now it's
looking much more like it would be advantageous for equality to simply
not raise an error on different types and just say, "Nope, they're not
equal."
The OP might want to know about type difference NOT implying unequal when
conversion can be done, as between numbers. E.g.,
(True, True, True)


BTW, this looks like a bug in the doc<->reality relationship:

Python 2.3 (#46, Jul 29 2003, 18:54:32) [MSC v.1200 32 bit (Intel)] on win32
Type "help", "copyright", "credits" or "license" for more information. Help on built-in function coerce:

coerce(...)
coerce(x, y) -> None or (x1, y1)

When x and y can be coerced to values of the same type, return a tuple
containing the coerced values. When they can't be coerced, return None.
Traceback (most recent call last):
File "<stdin>", line 1, in ?
TypeError: number coercion failed

Bad doc string or misimplementation? Or is it fixed in the latest release, (which I
haven't gotten around to installing yet)?

Regards,
Bengt Richter
 
B

Bengt Richter

Otherwise, wouldn't it imply that 2+'3' came out to 5 or '23'?
I was referring to the documented "return None" vs. the fact that it raised an exception.

Regards,
Bengt Richter
 

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

No members online now.

Forum statistics

Threads
473,780
Messages
2,569,611
Members
45,270
Latest member
TopCryptoTwitterChannels_

Latest Threads

Top