I want to use a python dict to store variable references and be able to assign the values pointed out by those references.
foo = \"foo\"
d = {\'foo\' : foo}
Python implements references to objects but it does not implement refs to variables. You can create a read-only binding to a local variable by using a local function:
foo = "foo"
def readfoo(newval):
return foo
d["foo"] = readfoo
foo = "bar"
d["foo"]() # returns "bar"
foo = "baz"
d["foo"]() # returns "baz"
This, however, is read-only since local function can only read vars from outside scope (I believe in Python 3 there's the nonlocal
keyword that changes this).
Depending on what you really want to achieve, the simplest workaround is to use one element lists instead. This way you wrap your values in objects (the lists) which can be referenced normally:
foo = ["foo"]
d["foo"] = foo
d["foo"][0] = "bar"
foo[0] # prints "bar"
Your idea won't work as strings are immutable - the value isn't changed, it is instead replaced. You could do something like this if you really felt the need to do it this way:
class MutableString:
def __init__(self, string):
self.string = string
def __str__(self):
return self.string
def __repr__(self):
return "MutableString("+repr(self.string)+")"
def set(self, string):
self.string = string
foo = MutableString("foo")
d = {'foo' : foo}
d['foo'].set("bar")
print(foo)
Which gives us bar
as output.
Another option would be to create an alternative dict
subclass that messes with __setitem__()
to produce a result like you want. The issue is, this isn't how others reading your code will expect this stuff to work. You are much better off changing your code so it doesn't rely on this sort of thing.
You can use setattr(profile, "mtoder_autoalpha", newvalue)
as an alternative to the settings dict. The way you do it won't work as you expect because strings(and booleans and tuples ...) are immutable, so when you change it its a new string you are creating, not editing the 'original' object/variable.