Reputation: 71
This may sound a bit funny, but this is what am trying to do:
I have two lists: myList1
and myList2
. I am passing these lists to a function that will perform a specific task depending on which list it receives (i.e., based on the name of the list, not content).
def listProcessor(data):
if data == 'myList1':
perform task1
else: #meaning data is myList2
perform task 2
Is there a way in Python 3 to inquire of the name of a list (or a tuple, dictionary, etc.) and do a comparison like this? Obviously, the way I am doing it here isn't working since it's comparing the content of the list 'data' to the single string 'myList1', which isn't working! :-).
Upvotes: 2
Views: 55
Reputation: 174700
There are a few ways to do this:
You can create separate functions if what needs to be done for each list really is completely separate.
You can update your function to either:
Take two lists as an argument:
def list_processor(list1=None, list2=None):
if list1:
# do stuff for list1
if list2:
# do stuff for list2
You can add an extra flag, identifying what kind of action to be performed, and set a default as well:
def list_processor(some_list=None, type_of_list=1):
if type_of_list == 1:
# do stuff with some_list as if it was list1
if type_of_list == 2:
# do stuff with some_list as if it was list2
You do not want to do what you initially proposed, for various reasons. One key reason is that in Python, what you may call variables in other languages are not "boxes to put stuff in" (as most textbooks refer to them).
In Python variables are actually just names that point to an object. The key thing is that multiple names can point to the same object; which will easily confuse your function if you rely on the lists "name".
Here is an example:
>>> a = [1,2,3]
>>> b = a
>>> b.append('hello')
>>> b is a
True
>>> b == a
True
>>> b
[1, 2, 3, 'hello']
>>> a
[1, 2, 3, 'hello']
In this example, both a
and b
are pointing to the same list object. What you do with a
affects b
.
Upvotes: 2
Reputation: 54223
So let's start with this: you really shouldn't do this. Data is just data in Python -- the identifier (e.g. the name you're using to talk about it) means nothing to the program logic itself. It's only meaningful to the programmer.
That said, there's ways to do what you're trying to do, and they're all the wrong thing to do. But they're possible, so let's talk about them.
globals()
will give you a dictionary with keys of identifiers and values of, um, values, for all objects currently in the global scope. This means that you can do:
def list_processor(data):
g = globals()
data_name = next((k for k,v in g.items() if v is data))
if data_name == 'myList1':
... # do whatever you want here
Note, however, that you're looking through EVERYTHING in the global scope. First off, that's dumb since it's slow, and secondly, it's dumb because it's buggy. What if myList1
isn't being passed from the global scope? What if it's a local variable inside a function that never hits the global scope? Now your tricky hack fails.
The correct way to do this is to perform some sort of introspection on the argument being passed in as "data
". For instance if myList1
always has 8 elements and myList2
always has 10:
def f_if_myList1(lst):
"""Do whatever we do if we pass myList1"""
...
def f_if_myList2(lst):
"""Do whatever we do if we pass myList2"""
...
def list_processor(data):
if len(data) == 8: # myList1!
f_if_myList1(data)
elif len(data) == 10:
f_if_myList2(data)
else:
# not sure. raise ValueError()?
Upvotes: 1