New submission from Nick Coghlan <[email protected]>:
(Note: I haven't categorised this yet, as I'm not sure how it *should* be
categorised)
Back when the __index__/nb_index slot was added, the focus was on allowing 3rd
party integer types to be used in places where potentially lossy conversion
with __int__/nb_int *wasn't* permitted.
However, this has led to an anomaly where the lossless conversion method
*isn't* tried implicitly for the potentially lossy int() and math.trunc()
calls, but is tried automatically in other contexts:
```
>>> import math
>>> class MyInt:
... def __index__(self):
... return 42
...
>>> int(MyInt())
Traceback (most recent call last):
File "<stdin>", line 1, in <module>
TypeError: int() argument must be a string, a bytes-like object or a number,
not 'MyInt'
>>> math.trunc(MyInt())
Traceback (most recent call last):
File "<stdin>", line 1, in <module>
TypeError: type MyInt doesn't define __trunc__ method
>>> hex(MyInt())
'0x2a'
>>> len("a" * MyInt())
42
```
Supporting int() requires also setting `__int__`:
```
>>> MyInt.__int__ = MyInt.__index__
>>> int(MyInt())
42
```
Supporting math.trunc() requires also setting `__trunc__`:
```
>>> MyInt.__trunc__ = MyInt.__index__
>>> math.trunc(MyInt())
42
```
(This anomaly was noticed by Eric Appelt while updating the int() docs to cover
the fallback to trying __trunc__ when __int__ isn't defined:
https://github.com/python/cpython/pull/6022#issuecomment-371695913)
----------
messages: 313515
nosy: Eric Appelt, mark.dickinson, ncoghlan
priority: normal
severity: normal
status: open
title: int() and math.trunc don't accept objects that only define __index__
_______________________________________
Python tracker <[email protected]>
<https://bugs.python.org/issue33039>
_______________________________________
_______________________________________________
Python-bugs-list mailing list
Unsubscribe:
https://mail.python.org/mailman/options/python-bugs-list/archive%40mail-archive.com