The Python Oracle

Test if a variable is a list or tuple

--------------------------------------------------
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: RPG Blues Looping

--

Chapters
00:00 Test If A Variable Is A List Or Tuple
00:34 Answer 1 Score 43
01:19 Accepted Answer Score 126
02:43 Answer 3 Score 665
02:51 Answer 4 Score 12
03:08 Thank you

--

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

--

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

--

Tags
#python #types #list

#avk47



ANSWER 1

Score 665


if type(x) is list:
    print 'a list'
elif type(x) is tuple:
    print 'a tuple'
else:
    print 'neither a tuple or a list'



ACCEPTED ANSWER

Score 126


Go ahead and use isinstance if you need it. It is somewhat evil, as it excludes custom sequences, iterators, and other things that you might actually need. However, sometimes you need to behave differently if someone, for instance, passes a string. My preference there would be to explicitly check for str or unicode like so:

import types
isinstance(var, types.StringTypes)

N.B. Don't mistake types.StringType for types.StringTypes. The latter incorporates str and unicode objects.

The types module is considered by many to be obsolete in favor of just checking directly against the object's type, so if you'd rather not use the above, you can alternatively check explicitly against str and unicode, like this:

isinstance(var, (str, unicode)):

Edit:

Better still is:

isinstance(var, basestring)

End edit

After either of these, you can fall back to behaving as if you're getting a normal sequence, letting non-sequences raise appropriate exceptions.

See the thing that's "evil" about type checking is not that you might want to behave differently for a certain type of object, it's that you artificially restrict your function from doing the right thing with unexpected object types that would otherwise do the right thing. If you have a final fallback that is not type-checked, you remove this restriction. It should be noted that too much type checking is a code smell that indicates that you might want to do some refactoring, but that doesn't necessarily mean you should avoid it from the getgo.




ANSWER 3

Score 43


There's nothing wrong with using isinstance as long as it's not redundant. If a variable should only be a list/tuple then document the interface and just use it as such. Otherwise a check is perfectly reasonable:

if isinstance(a, collections.abc.Iterable):
    # use as a container
else:
    # not a container!

This type of check does have some good use-cases, such as with the standard string startswith / endswith methods (although to be accurate these are implemented in C in CPython using an explicit check to see if it's a tuple - there's more than one way to solve this problem, as mentioned in the article you link to).

An explicit check is often better than trying to use the object as a container and handling the exception - that can cause all sorts of problems with code being run partially or unnecessarily.




ANSWER 4

Score 12


On Python 2.8 type(list) is list returns false
I would suggest comparing the type in this horrible way:

if type(a) == type([]) :
  print "variable a is a list"

(well at least on my system, using anaconda on Mac OS X Yosemite)