views:

133

answers:

4

PHP has a function called extract() which takes an associative array as the argument and creates local variables out of the keys whose values are assigned to the key's values. Is there a way to do this in Python? A quick google search didn't immediately show me how. I suspect there's a way with exec() but it'd be nice if there were some function to do it for me.

A: 

I found a similar question that's been answered on SO. The accepted answer suggests rolling your own extract equivalent for python.

ardsrk
+2  A: 

Try:

    locals().update(my_dict)

EDIT:

gnibbler has made a very valid point that locals shouldn't be modified (check: http://docs.python.org/library/functions.html#locals). Still, Python docs doesn't say it's not safe, it only says that changes to locals may not affect values of variables. Before answering the question I tried in my Python's 2.6 IDLE that updating locals actually works, both in global scope and inside a function. That's why I'm not deleting my answer, but instead I'm adding a warning that it might work under certain (platform-specific?) circumstances, but it's not guaranteed.

Tomasz Zielinski
It's not safe to make modifications to `locals()` http://docs.python.org/library/functions.html#locals
gnibbler
I didn't know, do you have any link supporting this? EDIT: I found here that locals() are read-only, which is not the case in IDLE 2.6 shell...
Tomasz Zielinski
It's not sage but it sufficient for a casual use.
e-satis
Link was cut from my comment above, it was example 8.12 at: http://diveintopython.org/html_processing/locals_and_globals.html
Tomasz Zielinski
A: 

Modifying locals() dict could have been a solution but docs say, http://docs.python.org/library/functions.html#

Note The contents of this dictionary should not be modified; changes may not affect the values of local and free variables used by the interpreter.

so the question is why you even need it? there may be better ways to achieve that whatever you are trying to achieve.

Also why can't you directly access dict or assign them to variables?

Anurag Uniyal
+2  A: 

Since it is not safe to modify the dict that locals() returns

>>> d={'a':6, 'b':"hello", 'c':set()}
>>> exec '\n'.join("%s=%r"%i for i in d.items())
>>> a
6
>>> b
'hello'
>>> c
set([])

But using exec like this is ugly. You should redesign so you don't need to dynamically add to your local namespace

Edit: See Mike's reservations about using repr in the comments.

>>> d={'a':6, 'b':"hello", 'c':set()}
>>> exec '\n'.join("%s=d['%s']"%(k,k) for k in d)
>>> id(d['c'])
3079176684L
>>> id(c)
3079176684L
gnibbler
Thanks, I'll use this. I mentioned above that I don't NEED this functionality, I just think it's neat to have.
Kevin
Although I don't think anyone *really* needs this functionality, one way to redesign your code would be to pass the dict into a function with **kwargs, where the dict will be cleanly unpacked into the local namespace.
Will Hardy
This code is broken. If you were to do this, you would reference the dict itself, not pull out reprs of the objects, which doesn't work in the general case. For example, you created a new set rather than using the passed one and if I had passed you a different type, like one I made without a useful `repr`, you'd be up the creek.
Mike Graham
@Mike, thanks for pointing that out - it is possible to use the references from the dict directly
gnibbler
@gnibbler. It's always possible
Mike Graham