Wenn Sie den Wert für E
, z. zu 2
könnten Sie Folgendes tun:
import yaml
def set_state(state):
with open('my_file.yaml') as f:
doc = yaml.load(f)
doc['B']['E'] = state
with open('my_file.yaml', 'w') as f:
yaml.dump(doc, f)
set_state(2)
auf den Wert von E
ersten Index auf B
zu erhalten.
Es gibt mehrere Probleme mit diesem in meiner Erfahrung:
Sie verwenden load()
, die in PyYAML ist ein unsicherer Betrieb ohne Vorwarnung. Ihre Daten können mit safe_load()
geladen werden, und selbst wenn es nicht möglich ist, ist es viel besser, safe_load()
zu erweitern, um Tags (und nur diese Tags) zu behandeln, als load()
zu erweitern.
Ihre Ausgabe wie folgt aussieht:
A: Sonstige
B: {C: Sonstige, D: null, E: 2}
nicht wie Sie Ihre Eingabe, so verwenden Sie die Option default_flow_style=False
etwas mit dem Original-Block-Layout zu erhalten.
Sie benötigen nicht dump()
, da Daten, die aus dict
s bestehen, und Grundelemente (und Listen) können mit safe_dump()
ausgegeben werden. Es gibt kein Sicherheitsproblem gibt, aber wenn Sie set_state()
nennen würden aus Versehen mit einem nicht-primitiver:
class Dice:
def __init__(self, sides):
self.sides = sides
set_state(Dice(6))
dann dump()
ohne weiteren Kommentar den nicht-portable erzeugen:
A: Sonstige
B:
C: Sonstige
D: null
E: !!python/object:__main__.Dice {sides: 6}
statt Heben einen Representer
Fehlers .
Alle Kommentare in Ihrer Originaldatei gehen verloren. PyYAML bewahrt diese nicht.
Mit PyYAML sollten Sie tun:
import yaml
def set_state(state):
with open('my_file.yaml') as f:
doc = yaml.safe_load(f)
doc['B']['E'] = state
with open('my_file.yaml', 'w') as f:
yaml.safe_dump(doc, f, default_flow_style=False)
set_state(2)
Wenn Sie auch Kommentare erhalten möchten, oder eine Mischung aus Block-Stil und Flow-Stil, den Sie beibehalten möchten haben, empfehle ich Ihnen ruamel.yaml
verwenden (Disclaimer: ich bin der Autor dieses Paket):
import pathlib
from ruamel.yaml import YAML
def set_state(state):
yaml = YAML()
mf = pathlib.Path('my_file.yaml')
doc = yaml.load(mf)
doc['B']['E'] = state
yaml.dump(doc, mf)
Dies hat das gleiche Ergebnis wie zuvor, mit der load()
Methode standardmäßig sicher zu sein, die Erhaltung Ihr Layout (plus alle Kommentare in der YAML-Datei, die Sie möglicherweise haben) und öffnen Sie die Path
Instanz zum Lesen oder Schreiben wie erforderlich (so dass Sie nicht die with
Anweisung benötigen, noch die doppelte Aktion des Aufrufs dump
und die w
zu open()
).
Verschachtelte Wörterbuch-Verwendung? '' 'doc ['B'] ['C']' ''? Nicht sicher, wie Pyyaml funktioniert, aber drucken Sie einfach aus, was '' 'doc ['B']' '' Ihnen gibt, wenn es ein Diktat ist, gut, einfach. – sascha
doc ['B'] ['C'] .. Es funktioniert! .. Es funktioniert .. Vielen Dank .. Frage mich, wie ich das verpasst habe! –
Verwenden Sie niemals PyYAML 'yaml.load()', es ist nicht notwendig und unsicher. – Anthon