namespace dictionaries ok?
Bengt Richter
bokr at oz.net
Tue Oct 25 16:55:52 EDT 2005
On Tue, 25 Oct 2005 16:20:21 GMT, Ron Adam <rrr at ronadam.com> wrote:
>Duncan Booth wrote:
>> Ron Adam wrote:
>>
>>>James Stroud wrote:
>>>
>>>>Here it goes with a little less overhead:
>>>>
>>>>
>>
>> <example snipped>
>>
>>>But it's not a dictionary anymore so you can't use it in the same places
>>>you would use a dictionary.
>>>
>>> foo(**n)
>>>
>>>Would raise an error.
>>>
>>>So I couldn't do:
>>>
>>> def foo(**kwds):
>>> kwds = namespace(kwds)
>>> kwds.bob = 3
>>> kwds.alice = 5
>>> ...
>>> bar(**kwds) #<--- do something with changed items
>>>
>>
>> I agree with Steven D'Aprano's reply, but if you are set on it you could
>> try this:
>>
>>
>>>>>class namespace(dict):
>>
>> def __init__(self, *args, **kw):
>> dict.__init__(self, *args, **kw)
>> self.__dict__ = self
>>
>>
>>
>>>>>n = namespace({'bob':1, 'carol':2, 'ted':3, 'alice':4})
>>>>>n.bob
>>
>> 1
>>
>>>>>n.bob = 3
>>>>>n['bob']
>>
>> 3
>>
>> The big problem of course with this sort of approach is that you cannot
>> then safely use any of the methods of the underlying dict as they could be
>> masked by values.
>>
>> P.S. James, *please* could you avoid top-quoting.
>
>Or worse, the dictionary would become not functional depending on what
>methods were masked.
>
>
>And this approach reverses that, The dict values will be masked by the
>methods, so the values can't effect the dictionary methods. But those
>specific values are only retrievable with the standard dictionary notation.
>
> class namespace(dict):
> __getattr__ = dict.__getitem__
> __setattr__ = dict.__setitem__
> __delattr__ = dict.__delitem__
>
> n = namespace()
> n.__getattr__ = 'yes' # doesn't mask __getattr__ method.
>
> print n['__getattr__'] -> 'yes'
>
>The value is there and __getattr__() still works. But n.__getattr__
>returns the method not the value.
>
>So is there a way to keep the functionality without loosing the methods?
>
>
>BTW, I agree with Steven concerning data structures. This really isn't
>a substitute for a data structure. Many keys will not work with this.
>
> n.my name = 'Ron'
> n.(1,2) = 25
> n.John's = [ ... ]
>
>The use case I'm thinking of is not as a shortcut for data structures,
>but instead, as a way to keep names as names, and maintaining those
>names in a group. Thus the namespace association.
>
> def foo(**kwds):
> kwds = namespace(kwds)
> print kwds.name
> print kwds.value
> ...
>
> name = 'ron'
> value = 25
> foo( name=name, position=position )
>
Just had the thought that if you want to add bindings on the fly modifying the
original object, you could use the __call__ method, e.g.,
>>> class NameSpace(dict):
... __getattr__ = dict.__getitem__
... __setattr__ = dict.__setitem__
... __delattr__ = dict.__delitem__
... def __call__(self, **upd):
... self.update(upd)
... return self
...
>>> def show(x): print '-- showing %r'%x; return x
...
>>> ns = NameSpace(initial=1)
>>> show(ns)
-- showing {'initial': 1}
{'initial': 1}
And updating with a second keyword on the fly:
>>> show(show(ns)(second=2))
-- showing {'initial': 1}
-- showing {'second': 2, 'initial': 1}
{'second': 2, 'initial': 1}
FWIW ;-)
Regards,
Bengt Richter
More information about the Python-list
mailing list