2011-12-28 21 views
13

Python辞書をシリアライズするときにPyYamlがキーと値のペアをどのように出力するかを制御するにはどうすればよいですか?PythonでのYamlのシリアライゼーション順序の制御

私はYamlをPythonスクリプトのシンプルなシリアライズフォーマットとして使用しています。私のYamlシリアル化されたオブジェクトは一種の「ドキュメント」を表します。そのため、使いやすさを最大限に高めるために、オブジェクトの「名前」フィールドをファイル内に最初に表示します。もちろん、私のオブジェクトの__getstate__によって返される値は辞書であり、Python辞書は順序付けされていないので、 "name"フィールドは出力のランダムな場所にシリアル化されます。

>>> import yaml 
>>> class Document(object): 
...  def __init__(self, name): 
...   self.name = name 
...   self.otherstuff = 'blah' 
...  def __getstate__(self): 
...   return self.__dict__.copy() 
... 
>>> doc = Document('obj-20111227') 
>>> print yaml.dump(doc, indent=4) 
!!python/object:__main__.Document 
otherstuff: blah 
name: obj-20111227 
+0

、同様の質問(この1年後のカップルを尋ねた)ここにあります:私の元のコードに適用され、解決策のようなものが見えますhttp://stackoverflow.com/q/16782112/877069 –

答えて

15

は私にPyYAMLとドキュメントやチケットを掘りの数時間かかったが、私は最終的に、通常のYAMLマップとしてOrderedDictをシリアル化する(ただし、秩序を維持する)ためのいくつかの概念実証コードをレイアウトthis commentを発見しました。

レコードの

>>> import yaml 
>>> from collections import OrderedDict 
>>> def dump_anydict_as_map(anydict): 
...  yaml.add_representer(anydict, _represent_dictorder) 
... 
>>> def _represent_dictorder(self, data): 
...  if isinstance(data, Document): 
...   return self.represent_mapping('tag:yaml.org,2002:map', data.__getstate__().items()) 
...  else: 
...   return self.represent_mapping('tag:yaml.org,2002:map', data.items()) 
... 
>>> class Document(object): 
...  def __init__(self, name): 
...   self.name = name 
...   self.otherstuff = 'blah' 
...  def __getstate__(self): 
...   d = OrderedDict() 
...   d['name'] = self.name 
...   d['otherstuff'] = self.otherstuff 
...   return d 
... 
>>> dump_anydict_as_map(Document) 
>>> doc = Document('obj-20111227') 
>>> print yaml.dump(doc, indent=4) 
!!python/object:__main__.Document 
name: obj-20111227 
otherstuff: blah 
-7

最後にチェックしたときに、Pythonの辞書は注文されませんでした。あなたが本当にそれらをしたい場合は、私はキーと値のペアのリストを使用することを強くお勧めします。

[ 
    ('key', 'value'), 
    ('key2', 'value2') 
] 

または、キーを使用してリストを定義し、正しい順序で配置します。

keys = ['key1', 'name', 'price', 'key2']; 
for key in keys: 
    print obj[key] 
+4

私の記事のように、私はPythonの辞書が順序付けられていないことを知っています。残念ながら、辞書とタプルのリストの間のYamlの可読性には大きな違いがありますので、私の場合はうまくいかないでしょう。 – Cerin

関連する問題