Python 的 ConfigParser 每个部分的唯一键
我阅读了 文档 的部分,并看到 ConfigParser
返回节中选项的键/值对列表。 我认为键在一个部分中不需要是唯一的,否则解析器只会返回一个映射。 我围绕这个假设设计了我的配置文件模式,然后悲伤地意识到事实并非如此:
>>> from ConfigParser import ConfigParser
>>> from StringIO import StringIO
>>> fh = StringIO("""
... [Some Section]
... spam: eggs
... spam: ham
... """)
>>> parser = ConfigParser()
>>> parser.readfp(fh)
>>> print parser.items('Some Section')
[('spam', 'ham')]
然后我返回并找到了我应该阅读的文档部分:
节通常存储在 内置词典。 替代 字典类型可以传递给 ConfigParser 构造函数。 例如, 如果传递了字典类型 对它的键进行排序,这些部分将是 在写回时排序,就像 每个部分中的键。
为了保留我现有的配置文件方案(我现在真的很喜欢;)我正在考虑传递一个如上所述的类似映射的对象,该对象会累积值而不是破坏它们。 有没有更简单的方法来防止我缺少的键/值崩溃? 我应该编写 ConfigParser 本身的一个变体,而不是制作一个疯狂的适配器(如果 ConfigParser 的实现发生更改,这可能会中断)?
我觉得这可能是那些“呃”时刻之一,我只看到了困难的解决方案。
[编辑:] 这是我如何多次使用同一个键的更精确示例:
[Ignored Paths]
ignore-extension: .swp
ignore-filename: tags
ignore-directory: bin
我不喜欢逗号分隔列表语法,因为当您将其缩放到许多价值观; 例如,由五十个扩展名组成的逗号分隔列表的可读性不是特别好。
I read the part of the docs and saw that the ConfigParser
returns a list of key/value pairs for the options within a section. I figured that keys did not need to be unique within a section, otherwise the parser would just return a mapping. I designed my config file schema around this assumption, then sadly realized that this is not the case:
>>> from ConfigParser import ConfigParser
>>> from StringIO import StringIO
>>> fh = StringIO("""
... [Some Section]
... spam: eggs
... spam: ham
... """)
>>> parser = ConfigParser()
>>> parser.readfp(fh)
>>> print parser.items('Some Section')
[('spam', 'ham')]
Then I went back and found the part of the docs that I should have read:
Sections are normally stored in a
builtin dictionary. An alternative
dictionary type can be passed to the
ConfigParser constructor. For example,
if a dictionary type is passed that
sorts its keys, the sections will be
sorted on write-back, as will be the
keys within each section.
To keep my existing configuration file scheme (which I really like now ;) I'm thinking of passing a mapping-like object as mentioned above that accumulates values instead of clobbering them. Is there a simpler way to prevent key/value collapse that I'm missing? Instead of making a crazy adapter (that could break if ConfigParser
's implementation changes) should I just write a variant of the ConfigParser
itself?
I feel like this may be one of those 'duh' moments where I'm only seeing the difficult solutions.
[Edit:] Here's a more precise example of how I'd like to use the same key multiple times:
[Ignored Paths]
ignore-extension: .swp
ignore-filename: tags
ignore-directory: bin
I dislike the comma-delimited-list syntax because it's hard on the eyes when you scale it to many values; for example, a comma delimited list of fifty extensions would not be particularly readable.
如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。
绑定邮箱获取回复消息
由于您还没有绑定你的真实邮箱,如果其他用户或者作者回复了您的评论,将不能在第一时间通知您!
发布评论
评论(2)
ConfigParser 并不是为处理此类情况而设计的。 此外,你的配置文件对我来说没有意义。
ConfigParser 为每个部分提供了一个类似字典的结构,因此当您调用 parser.items(section) 时,我期望与 dict.items() 类似的输出,它只是键/值元组的列表。 我永远不会期望看到类似的内容:
更不用说,您期望以下行为如何?:
这是检索值的预期方式。
如果您想为同一个键存储多个值,我建议在您的配置文件中使用类似的内容:
在您的代码中:
当然,这仅适用于本身不包含逗号或不处理引用的值。 为此,您应该采用更高级的技术(请参阅这个和这个< /a>)。
编辑:如果您不介意额外的依赖项,您可以查看 ConfigObj,它本身支持列表作为值类型。
ConfigParser isn't designed to handle such conditions. Furthermore, your config file doesn't make sense to me.
ConfigParser gives you a dict-like structure for each section, so when you call parser.items(section), I'm expecting similar output to dict.items(), which is just a list of key/value tuples. I would never expect to see something like:
Not to mention, how would you expect the following to behave?:
Which is the intended way to retrieve values.
If you want to store multiple values for the same key, I would suggest something like this in your config file:
And this in your code:
Of course, this will only work for values that don't contain commas themselves or handle quoting. For that, you should employ a more advanced technique (see this and this).
EDIT: If you don't mind the extra dependency, You could check out ConfigObj, which natively supports lists as a value type.
ConfigParser 的这种缺陷是 pyglet 使用 epydoc 的修补版本,用此 简单格式:
如果您不需要部分 - 这种方法可以有用的。
This deficiency of ConfigParser is the reason why pyglet used patched version of epydoc to replace ConfigParser ini with this simple format:
If you don't need sections - this approach can be useful.