[Python-Dev] Numeric conversions

Guido van Rossum guido@python.org
Mon, 03 Jun 2002 01:23:03 -0400


> The following small program is giving me some unexpected results with
> Python 2.2.1:
> 
> class Int(object):
>     def __int__(self): return 10
> 
> class Float(object):
>     def __float__(self): return 10.0
> 
> class Long(object):
>     def __long__(self): return 10L
> 
> class Complex(object):
>     def __complex__(self): return (10+0j)
> 
> def attempt(f,arg):
>     try:
>         return f(arg)
>     except Exception,e:
>         return str(e.__class__.__name__)+': '+str(e)
> 
> for f in int,float,long,complex:
>     for t in Int,Float,Long,Complex:
>         print f.__name__ + '(' + t.__name__ + ')\t\t',
>         print attempt(f,t())
> 
> ----- results ------
> 
> int(Int)                10
> int(Float)              TypeError: object can't be converted to int
> int(Long)               TypeError: object can't be converted to int
> int(Complex)            TypeError: object can't be converted to int
> 
> *** OK, int() seems to work as expected
> 
> float(Int)              TypeError: float() needs a string argument
> float(Float)            10.0
> float(Long)             TypeError: float() needs a string argument
> float(Complex)          TypeError: float() needs a string argument
> 
> *** float() seems to work, but what's with the error message about strings?

Sloppy coding.  float(), like int() and long(), takes either a number
or a string.  Raymond Hettinger fixed this in CVS in response to SF
bug 551673, about two weeks ago. :-)

> long(Int)               TypeError: object can't be converted to long
> long(Float)             TypeError: object can't be converted to long
> long(Long)              10
> long(Complex)           TypeError: object can't be converted to long
> 
> **** OK, long seems to work as expected
> 
> complex(Int)            TypeError: complex() arg can't be converted to
> complex
> complex(Float)          (10+0j)
> complex(Long)           TypeError: complex() arg can't be converted to
> complex
> complex(Complex)        TypeError: complex() arg can't be converted to
> complex
> 
> **** I can understand complex() handling Float implicitly, but only if it
> also handles Complex! And if it does handle Float implicitly, shouldn't all
> of these handle everything?

The signature of complex() is different -- it takes two float
arguments, the real and imaginary part.

It doesn't take Complex() because of a bug: it only looks for
__complex__ if the argument is a classic instance.  Maybe Raymond can
fix this?  I've added a bug report: python.org/sf/563740

--Guido van Rossum (home page: http://www.python.org/~guido/)