mirror of https://github.com/python/cpython.git
Issue #4910 (1st patch of a series): fix int() and the corresponding
PyNumber_Int/PyNumber_Long API function so that it no longer attempts to call the __long__ method for conversion. Only the __int__ and __trunc__ methods are used. (This removes a major remaining use of the nb_long slot from the Python 3.x core.) Thanks Benjamin for review.
This commit is contained in:
parent
7c2b66cc02
commit
e5e298f875
|
@ -367,7 +367,7 @@ def test_long(self):
|
||||||
|
|
||||||
|
|
||||||
def test_conversion(self):
|
def test_conversion(self):
|
||||||
# Test __long__()
|
# Test __int__()
|
||||||
class ClassicMissingMethods:
|
class ClassicMissingMethods:
|
||||||
pass
|
pass
|
||||||
self.assertRaises(TypeError, int, ClassicMissingMethods())
|
self.assertRaises(TypeError, int, ClassicMissingMethods())
|
||||||
|
@ -410,18 +410,32 @@ def __int__(self):
|
||||||
class Classic:
|
class Classic:
|
||||||
pass
|
pass
|
||||||
for base in (object, Classic):
|
for base in (object, Classic):
|
||||||
class LongOverridesTrunc(base):
|
class IntOverridesTrunc(base):
|
||||||
def __long__(self):
|
def __int__(self):
|
||||||
return 42
|
return 42
|
||||||
def __trunc__(self):
|
def __trunc__(self):
|
||||||
return -12
|
return -12
|
||||||
self.assertEqual(int(LongOverridesTrunc()), 42)
|
self.assertEqual(int(IntOverridesTrunc()), 42)
|
||||||
|
|
||||||
class JustTrunc(base):
|
class JustTrunc(base):
|
||||||
def __trunc__(self):
|
def __trunc__(self):
|
||||||
return 42
|
return 42
|
||||||
self.assertEqual(int(JustTrunc()), 42)
|
self.assertEqual(int(JustTrunc()), 42)
|
||||||
|
|
||||||
|
class JustLong(base):
|
||||||
|
# test that __long__ no longer used in 3.x
|
||||||
|
def __long__(self):
|
||||||
|
return 42
|
||||||
|
self.assertRaises(TypeError, int, JustLong())
|
||||||
|
|
||||||
|
class LongTrunc(base):
|
||||||
|
# __long__ should be ignored in 3.x
|
||||||
|
def __long__(self):
|
||||||
|
return 42
|
||||||
|
def __trunc__(self):
|
||||||
|
return 1729
|
||||||
|
self.assertEqual(int(LongTrunc()), 1729)
|
||||||
|
|
||||||
for trunc_result_base in (object, Classic):
|
for trunc_result_base in (object, Classic):
|
||||||
class Integral(trunc_result_base):
|
class Integral(trunc_result_base):
|
||||||
def __int__(self):
|
def __int__(self):
|
||||||
|
|
|
@ -12,6 +12,10 @@ What's New in Python 3.1 alpha 0
|
||||||
Core and Builtins
|
Core and Builtins
|
||||||
-----------------
|
-----------------
|
||||||
|
|
||||||
|
- Issue #4910: Builtin int() function and PyNumber_Long/PyNumber_Int API
|
||||||
|
function no longer attempt to call the __long__ slot to convert an object
|
||||||
|
to an integer. Only the __int__ and __trunc__ slots are examined.
|
||||||
|
|
||||||
- Issue #4893: Use NT threading on CE.
|
- Issue #4893: Use NT threading on CE.
|
||||||
|
|
||||||
- Issue #4915: Port sysmodule to Windows CE.
|
- Issue #4915: Port sysmodule to Windows CE.
|
||||||
|
|
|
@ -1379,19 +1379,7 @@ PyNumber_Long(PyObject *o)
|
||||||
}
|
}
|
||||||
return res;
|
return res;
|
||||||
}
|
}
|
||||||
if (m && m->nb_long) { /* This should include subclasses of long */
|
if (PyLong_Check(o)) /* An int subclass without nb_int */
|
||||||
/* Classic classes always take this branch. */
|
|
||||||
PyObject *res = m->nb_long(o);
|
|
||||||
if (res && !PyLong_Check(res)) {
|
|
||||||
PyErr_Format(PyExc_TypeError,
|
|
||||||
"__long__ returned non-long (type %.200s)",
|
|
||||||
res->ob_type->tp_name);
|
|
||||||
Py_DECREF(res);
|
|
||||||
return NULL;
|
|
||||||
}
|
|
||||||
return res;
|
|
||||||
}
|
|
||||||
if (PyLong_Check(o)) /* A long subclass without nb_long */
|
|
||||||
return _PyLong_Copy((PyLongObject *)o);
|
return _PyLong_Copy((PyLongObject *)o);
|
||||||
trunc_func = PyObject_GetAttr(o, trunc_name);
|
trunc_func = PyObject_GetAttr(o, trunc_name);
|
||||||
if (trunc_func) {
|
if (trunc_func) {
|
||||||
|
|
Loading…
Reference in New Issue