Specyfikacja YAML wyraźnie stwierdza, że kluczowa kolejność w mapowaniu to "szczegół reprezentacyjny", na który nie można polegać. W związku z tym plik ustawień jest już nieprawidłowy, jeśli opiera się na mapowaniu, a lepiej użyć prawidłowego YAML, o ile to możliwe.
Oczywiście YAML jest rozszerzalny i nic nie stoi na przeszkodzie, aby dodać "uporządkowane odwzorowanie" do plików ustawień. Na przykład:
!omap setting1:
name: [item,item]
name1: text
!omap anothersetting2:
name: [item,item]
!omap sub_setting:
name :[item,item]
Nie wspominając, który moduł yaml
używasz. W standardowej bibliotece nie ma takiego modułu, a w PyPI są co najmniej dwa pakiety, które zapewniają moduły o tej nazwie. Jednak domyślam się, że to PyYAML, ponieważ o ile wiem, jest to najbardziej popularne.
Opisane powyżej rozszerzenie można z łatwością analizować za pomocą PyYAML. Zobacz http://pyyaml.org/ticket/29:
def omap_constructor(loader, node):
return loader.construct_pairs(node)
yaml.add_constructor(u'!omap', omap_constructor)
Teraz, zamiast:
{'anothersetting2': {'name': ['item', 'item'],
'sub_setting': 'name :[item,item]'},
'setting1': {'name': ['item', 'item'], 'name1': 'text'}}
Dostaniesz to:
(('anothersetting2', (('name', ['item', 'item']),
('sub_setting', ('name, [item,item]'),))),
('setting1', (('name', ['item', 'item']), ('name1', 'text'))))
Oczywiście to daje tuple
kluczowych wartości tuple
s, ale możesz łatwo napisać construct_ordereddict i zamiast tego uzyskać OrderedDict
. Można również napisać reprezentację, która przechowuje obiekty s, jeśli trzeba wyprowadzać, jak również dane wejściowe.
Jeśli naprawdę chcesz podłączyć PyYAML, aby używał domyślnego odwzorowania OrderedDict
zamiast dict
, to całkiem łatwo zrobić, jeśli pracujesz już bezpośrednio nad obiektami analizatora składni, ale trudniej, jeśli chcesz trzymać się metody komfortu na wysokim poziomie. Na szczęście powyższy bilet ma implementację, której możesz użyć.Pamiętaj tylko, że nie używasz już prawdziwego YAML, ale wariant, więc każde inne oprogramowanie, które zajmuje się Twoimi plikami, może i prawdopodobnie się zepsuje.
Po pierwsze, jest ten "PyYAML", czy coś innego? Nie ma wbudowanego modułu 'yaml' i co najmniej dwóch pakietów PyPI, które dają ci moduł' yaml'. Generalnie, gdy używasz modułu innej firmy, powinieneś powiedzieć, skąd go bierzesz. – abarnert
Niezależnie od tego, jakiego modułu używasz, musisz przechwycić sposób, w jaki konwertuje on węzły mapowania na język Python, więc używa 'collection.OrderedDict' zamiast' dict'. Z innymi modułami poza PyYAML, nie mam pojęcia. W przypadku 'PyYAML' jest to zdecydowanie możliwe, ale jest skomplikowane, jeśli trzymasz się metod wygody na wysokim poziomie. Gdzie indziej, ktoś wspomniał, że łatwiej jest go zmonopolować, niż używać zamierzonych haków. – abarnert
Im za pomocą PyYAML jako tytuł tego pytania sugeruje ... -> PyYAML: Kontrola kolejności elementów wywołanych przez yaml.load(). Dzięki za radę!! – zzart