[Python-Dev] defaultdict proposal round three

Fuzzyman fuzzyman at voidspace.org.uk
Wed Feb 22 10:02:33 CET 2006


Greg Ewing wrote:
> Fuzzyman wrote:
>
>   
>> I've had problems in code that needs to treat strings, lists and
>> dictionaries differently (assigning values to a container where all
>> three need different handling) and telling the difference but allowing
>> duck typing is *problematic*.
>>     
>
> You need to rethink your design so that you don't
> have to make that kind of distinction.

Well... to *briefly* explain the use case, it's for value assignment in 
ConfigObj.

It basically accepts as valid values strings and lists of strings [#]_. 
You can also create new subsections by assigning a dictionary.

It needs to be able to recognise lists in order to check each list 
member is a string. (See note below, it still needs to be able to 
recognise lists when writing, even if it is not doing type checking on 
assignment.)

It needs to be able to recognise dictionaries in order to create a new 
section instance (rather than directly assigning the dictionary).

This is *terribly* convenient for the user (trivial example of creating 
a new config file programatically) :

from configobj import ConfigObj
cfg = ConfigObj(newfilename)
cfg['key'] = 'value'
cfg['key2'] = ['value1', 'value2', 'value3']
cfg['section'] = {'key': 'value', 'key2': ['value1', 'value2', 'value3']}
cfg.write()

Writes out :

key = value
key2 = value1, value2, value3
[section]
key = value
key2 = value1, value2, value3

(Note none of those values needed quoting, so they aren't.)

Obviously I could force the creation of sections and the assignment of 
list values to use separate methods, but it's much less readable and 
unnecessary.

The code as is works and has a nice API. It still needs to be able to 
tell what *type* of value is being assigned.

Mapping and sequence protocols are so loosely defined that in order to 
support 'list like objects' and 'dictionary like objects' some arbitrary 
decision about what methods they should support has to be made. (For 
example a read only mapping container is unlikely to implement 
__setitem__ or methods like update).

At first we defined a mapping object as one that defines __getitem__ and 
keys (not update as  I previously said), and list like objects as ones 
that define __getitem__ and *not* keys. For strings we required a 
basestring subclass. In the end I think we ripped this out and just 
settled on isinstance tests.

All the best,

Michael Foord


.. [#] Although it has two modes. In the 'default' mode you can assign 
any object as a value and a string representation is written out. A more 
strict mode checks values at the point you assign  them - so errors will 
be raised at that point rather than propagating into the config file. 
When writing you still need to able to recognise lists because each 
element is properly quoted.
-------------- next part --------------
An HTML attachment was scrubbed...
URL: http://mail.python.org/pipermail/python-dev/attachments/20060222/2a628df3/attachment-0001.html 


More information about the Python-Dev mailing list