The Python Oracle

How can I check if my python object is a number?

--------------------------------------------------
Rise to the top 3% as a developer or hire one of them at Toptal: https://topt.al/25cXVn
--------------------------------------------------

Music by Eric Matyas
https://www.soundimage.org
Track title: A Thousand Exotic Places Looping v001

--

Chapters
00:00 How Can I Check If My Python Object Is A Number?
00:16 Answer 1 Score 246
00:32 Accepted Answer Score 346
01:24 Answer 3 Score 64
01:59 Thank you

--

Full question
https://stackoverflow.com/questions/4187...

--

Content licensed under CC BY-SA
https://meta.stackexchange.com/help/lice...

--

Tags
#python #types #numbers

#avk47



ACCEPTED ANSWER

Score 346


Test if your variable is an instance of numbers.Number:

>>> import numbers
>>> import decimal
>>> [isinstance(x, numbers.Number) for x in (0, 0.0, 0j, decimal.Decimal(0))]
[True, True, True, True]

This uses ABCs and will work for all built-in number-like classes, and also for all third-party classes if they are worth their salt (registered as subclasses of the Number ABC).

However, in many cases you shouldn't worry about checking types manually - Python is duck typed and mixing somewhat compatible types usually works, yet it will barf an error message when some operation doesn't make sense (4 - "1"), so manually checking this is rarely really needed. It's just a bonus. You can add it when finishing a module to avoid pestering others with implementation details.

This works starting with Python 2.6. On older versions you're pretty much limited to checking for a few hardcoded types.




ANSWER 2

Score 246


Python 3:

isinstance(x, (int, float, complex)) and not isinstance(x, bool)

Python 2:

isinstance(x, (int, long, float, complex)) and not isinstance(x, bool)

Note that this answer works incorrectly for Numpy objects.




ANSWER 3

Score 64


Use Number from the numbers module to test isinstance(n, Number) (available since 2.6).

isinstance(n, numbers.Number)

Here it is in action with various kinds of numbers and one non-number:

>>> from numbers import Number
... from decimal import Decimal
... from fractions import Fraction
... for n in [2, 2.0, Decimal('2.0'), complex(2,0), Fraction(2,1), '2']:
...     print '%15s %s' % (n.__repr__(), isinstance(n, Number))
              2 True
            2.0 True
 Decimal('2.0') True
         (2+0j) True
 Fraction(2, 1) True
            '2' False

This is, of course, contrary to duck typing. If you are more concerned about how an object acts rather than what it is, perform your operations as if you have a number and use exceptions to tell you otherwise.