Is there any way to have Python operators line "==" and ">" return ints instead of bools. I know that I could use the int function (int(1 == 1)
) or add 0 ((1 == 1) + 0
) but I was wondering if there was an easy way to do it. Like when you want division to return floats you could type from __future__ import division
. Is there any way to do this with operators returning ints? Or could I make a class extending __future__._Feature
that would do what I want?

- 3,875
- 7
- 43
- 67
-
1This seems like a pretty strange request, with no clear motivation. Would you like to explain a bit more about why you believe you need this? – Greg Hewgill May 05 '10 at 23:11
-
I am making a stack based programming language. If you use greater than or less than in it it pops two items from the stack and does something like `stack.push(stack.pop() > stack.pop())`. If I wanted to then print the integer it would take the top of the stack and convert it to a string using `str(stack.pop())` and print that. I would want 1 or 0 to be printed but instead it prints "True" or "False". This creates complications when making things like if statements. – None May 05 '10 at 23:17
-
5Modifying fundamental operators in Python is not the answer. You either don't want Python's > (write your own function), or you want different behavior for converting booleans to strings (write your own function). – Glenn Maynard May 05 '10 at 23:30
6 Answers
You cant override the built-in comparison functions. In some sense the comparison operators are already returning int
. bool
is a subclass of int
, so you can do anything to it that you can do to a int. The question then becomes why would you want to have comparisons return int objects, not bool objects?

- 53,288
- 15
- 90
- 97
You can have the comparison operators of your custom classes return whatever you like -- simply implement the relevant methods (__eq__
, __ne__
, __gt__
, __lt__
, __ge__
, __le__
) to return what you want. For objects that you don't control you cannot change this, but there should be no need to: bools are ints, because of the Liskov substitution principle. Code that notices a difference between the bool returned by the builtin types' __eq__
methods and any other integer is using the result wrong.
The __future__
module isn't relevant here; you can't use it to do whatever you want, you can only use it to change specific settings that were added to Python. You can turn division into true division with the __future__
import because that's what was added to Python. The only way to add more __future__
imports is by modifying Python itself.

- 130,178
- 23
- 148
- 122
Based on your clarification, you might change your comparison operator to something like:
stack.push(1 if stack.pop() > stack.pop() else 0)
This will convert the boolean result of >
to 1
or 0
as you would like.
Also, be careful about calling stack.pop()
twice in the same expression. You don't know (for sure) what order the arguments will be evaluated in, and different implementations of Python may very well pop the arguments in a different order. You will need to use temporary variables:
x = stack.pop()
y = stack.pop()
stack.push(1 if x > y else 0)

- 951,095
- 183
- 1,149
- 1,285
-
I did the different `stack.pop()`s in the code but was trying to compact them in my comment. Thanks anyway though. – None May 05 '10 at 23:34
-
The evaluation order of expressions is specified in the language reference (http://docs.python.org/reference/expressions.html#evaluation-order). That said, having function calls with side effects inside a non-trivial expression is usually a bad idea. – Ants Aasma May 07 '10 at 11:47
On your own objects, it is easy to override each comparison operator. For built-ins, the override methods are "read only" so all my attempts to set them don't pan out.
>>> class foo:
def __lt__(self, other):
return cmp(5, other)
>>> f = foo()
>>> f<3
1
>>> f<7
-1
>>> f<5
0
>>> j=""
>>> j.__lt__=lambda other: cmp(5, other)
Traceback (most recent call last):
File "<stdin>", line 1, in ?
AttributeError: 'str' object attribute '__lt__' is read-only

- 2,001
- 1
- 19
- 21
Cast your bool to an int?
>>> int(True)
1
>>> int(False)
0
Or cast that to a str?
>>> str(int(True))
'1'
>>> str(int(False))
'0'

- 3,851
- 3
- 34
- 35
No, you can't. When Guido unified types and classes, he found a way to override the behavior of built-in types (due to the way he implemented things), but he declared it a bug and plugged the loophole. Changing the behavior of built-in types (except for your example - importing division from future, which is there for a good reason) is forbidden.
Sorry, but I can't find the mailing list post. I remember it though, as it was quite interesting.

- 6,981
- 1
- 30
- 29