Wie kann ich gültiges XML in C # generieren?
Wie kann ich gültiges XML in C # generieren?
Antworten:
Das hängt vom Szenario ab. XmlSerializer
ist sicherlich eine Möglichkeit und hat den Vorteil, direkt auf ein Objektmodell abzubilden. In .NET 3.5 XDocument
usw. sind auch sehr freundlich. Wenn die Größe sehr groß ist, dann XmlWriter
ist dein Freund.
Ein XDocument
Beispiel:
Console.WriteLine(
new XElement("Foo",
new XAttribute("Bar", "some & value"),
new XElement("Nested", "data")));
Oder das gleiche mit XmlDocument
:
XmlDocument doc = new XmlDocument();
XmlElement el = (XmlElement)doc.AppendChild(doc.CreateElement("Foo"));
el.SetAttribute("Bar", "some & value");
el.AppendChild(doc.CreateElement("Nested")).InnerText = "data";
Console.WriteLine(doc.OuterXml);
Wenn Sie einen großen Datenstrom schreiben , beansprucht jeder der DOM-Ansätze (wie XmlDocument
/ XDocument
usw.) schnell viel Speicher. Wenn Sie also eine 100-MB-XML-Datei aus CSV schreiben , sollten Sie dies in Betracht ziehen XmlWriter
. Dies ist primitiver (ein einmal geschriebener Feuerwehrschlauch), aber sehr effizient (stellen Sie sich hier eine große Schleife vor):
XmlWriter writer = XmlWriter.Create(Console.Out);
writer.WriteStartElement("Foo");
writer.WriteAttributeString("Bar", "Some & value");
writer.WriteElementString("Nested", "data");
writer.WriteEndElement();
Zum Schluss über XmlSerializer
:
[Serializable]
public class Foo
{
[XmlAttribute]
public string Bar { get; set; }
public string Nested { get; set; }
}
...
Foo foo = new Foo
{
Bar = "some & value",
Nested = "data"
};
new XmlSerializer(typeof(Foo)).Serialize(Console.Out, foo);
Dies ist ein schönes Modell für die Zuordnung zu Klassen usw.; Es kann jedoch zu viel des Guten sein, wenn Sie etwas Einfaches tun (oder wenn das gewünschte XML keine direkte Korrelation zum Objektmodell hat). Ein weiteres Problem XmlSerializer
ist, dass unveränderliche Typen nicht gerne serialisiert werden: Alles muss einen öffentlichen Getter und Setter haben (es sei denn, Sie tun alles selbst durch Implementierung IXmlSerializable
, in diesem Fall haben Sie durch die Verwendung nicht viel gewonnen XmlSerializer
).
Das Beste, was ich je versucht habe, ist LINQ to XSD (was den meisten Entwicklern unbekannt ist). Sie geben ihm ein XSD-Schema und es generiert im Hintergrund ein perfekt zugeordnetes vollständiges stark typisiertes Objektmodell (basierend auf LINQ to XML), mit dem Sie sehr einfach arbeiten können - und es aktualisiert und validiert Ihr Objektmodell und XML in Echtzeit. Während es noch "Vorschau" ist, habe ich keine Fehler damit festgestellt.
Wenn Sie ein XSD-Schema haben, das folgendermaßen aussieht:
<xs:element name="RootElement">
<xs:complexType>
<xs:sequence>
<xs:element name="Element1" type="xs:string" />
<xs:element name="Element2" type="xs:string" />
</xs:sequence>
<xs:attribute name="Attribute1" type="xs:integer" use="optional" />
<xs:attribute name="Attribute2" type="xs:boolean" use="required" />
</xs:complexType>
</xs:element>
Dann können Sie einfach XML wie folgt erstellen:
RootElement rootElement = new RootElement;
rootElement.Element1 = "Element1";
rootElement.Element2 = "Element2";
rootElement.Attribute1 = 5;
rootElement.Attribute2 = true;
Oder laden Sie einfach ein XML aus einer Datei wie folgt:
RootElement rootElement = RootElement.Load(filePath);
Oder speichern Sie es so:
rootElement.Save(string);
rootElement.Save(textWriter);
rootElement.Save(xmlWriter);
rootElement.Untyped
liefert das Element auch in Form eines XElement (von LINQ bis XML).
RootElement
XmlWriter ist der schnellste Weg, um gutes XML zu schreiben. XDocument, XMLDocument und einige andere funktionieren ebenfalls gut, sind jedoch nicht für das Schreiben von XML optimiert. Wenn Sie das XML so schnell wie möglich schreiben möchten, sollten Sie auf jeden Fall XmlWriter verwenden.
In der Vergangenheit habe ich mein XML-Schema erstellt und dann mit einem Tool C # -Klassen generiert, die in dieses Schema serialisiert werden. Das XML-Schemadefinitionstool ist ein Beispiel
http://msdn.microsoft.com/en-us/library/x6c1kb0s(VS.71).aspx
Ich denke, diese Ressource sollte für ein moderates Speichern / Laden von XML ausreichen: Lesen / Schreiben von XML mit C # .
Meine Aufgabe war es, Noten zu speichern. Ich habe mich für XML entschieden, weil .NET vermutlich so ausgereift ist, dass eine einfache Lösung für die Aufgabe möglich ist. Ich lag richtig :)
Dies ist mein Prototyp der Songdatei:
<music judul="Kupu-Kupu yang Lucu" pengarang="Ibu Sud" tempo="120" birama="4/4" nadadasar="1=F" biramapembilang="4" biramapenyebut="4">
<not angka="1" oktaf="0" naikturun="" nilai="1"/>
<not angka="2" oktaf="0" naikturun="" nilai="0.5"/>
<not angka="5" oktaf="1" naikturun="/" nilai="0.25"/>
<not angka="2" oktaf="0" naikturun="\" nilai="0.125"/>
<not angka="1" oktaf="0" naikturun="" nilai="0.0625"/>
</music>
Das lässt sich ganz einfach lösen:
Zum Speichern in Datei:
private void saveToolStripMenuItem_Click(object sender, EventArgs e)
{
saveFileDialog1.Title = "Save Song File";
saveFileDialog1.Filter = "Song Files|*.xsong";
if (saveFileDialog1.ShowDialog() == DialogResult.OK)
{
FileStream fs = new FileStream(saveFileDialog1.FileName, FileMode.Create);
XmlTextWriter w = new XmlTextWriter(fs, Encoding.UTF8);
w.WriteStartDocument();
w.WriteStartElement("music");
w.WriteAttributeString("judul", Program.music.getTitle());
w.WriteAttributeString("pengarang", Program.music.getAuthor());
w.WriteAttributeString("tempo", Program.music.getTempo()+"");
w.WriteAttributeString("birama", Program.music.getBirama());
w.WriteAttributeString("nadadasar", Program.music.getNadaDasar());
w.WriteAttributeString("biramapembilang", Program.music.getBiramaPembilang()+"");
w.WriteAttributeString("biramapenyebut", Program.music.getBiramaPenyebut()+"");
for (int i = 0; i < listNotasi.Count; i++)
{
CNot not = listNotasi[i];
w.WriteStartElement("not");
w.WriteAttributeString("angka", not.getNot() + "");
w.WriteAttributeString("oktaf", not.getOktaf() + "");
String naikturun="";
if(not.isTurunSetengah())naikturun="\\";
else if(not.isNaikSetengah())naikturun="/";
w.WriteAttributeString("naikturun",naikturun);
w.WriteAttributeString("nilai", not.getNilaiNot()+"");
w.WriteEndElement();
}
w.WriteEndElement();
w.Flush();
fs.Close();
}
}
Zum Laden der Datei:
openFileDialog1.Title = "Open Song File";
openFileDialog1.Filter = "Song Files|*.xsong";
if (openFileDialog1.ShowDialog() == DialogResult.OK)
{
FileStream fs = new FileStream(openFileDialog1.FileName, FileMode.Open);
XmlTextReader r = new XmlTextReader(fs);
while (r.Read())
{
if (r.NodeType == XmlNodeType.Element)
{
if (r.Name.ToLower().Equals("music"))
{
Program.music = new CMusic(r.GetAttribute("judul"),
r.GetAttribute("pengarang"),
r.GetAttribute("birama"),
Convert.ToInt32(r.GetAttribute("tempo")),
r.GetAttribute("nadadasar"),
Convert.ToInt32(r.GetAttribute("biramapembilang")),
Convert.ToInt32(r.GetAttribute("biramapenyebut")));
}
else
if (r.Name.ToLower().Equals("not"))
{
CNot not = new CNot(Convert.ToInt32(r.GetAttribute("angka")), Convert.ToInt32(r.GetAttribute("oktaf")));
if (r.GetAttribute("naikturun").Equals("/"))
{
not.setNaikSetengah();
}
else if (r.GetAttribute("naikturun").Equals("\\"))
{
not.setTurunSetengah();
}
not.setNilaiNot(Convert.ToSingle(r.GetAttribute("nilai")));
listNotasi.Add(not);
}
}
else
if (r.NodeType == XmlNodeType.Text)
{
Console.WriteLine("\tVALUE: " + r.Value);
}
}
}
}
}
Für einfache Fälle würde ich auch empfehlen, sich XmlOutput als fließende Schnittstelle zum Erstellen von Xml anzusehen .
XmlOutput eignet sich hervorragend für die einfache Erstellung von XML mit lesbarem und wartbarem Code, während gültige XML-Dateien generiert werden. Der ursprüngliche Beitrag enthält einige großartige Beispiele.
Wie oben.
Ich benutze stringbuilder.append ().
Sehr einfach, und Sie können dann xmldocument.load (strinbuilder-Objekt als Parameter) ausführen.
Sie werden wahrscheinlich feststellen, dass Sie string.concat im Parameter append verwenden, dies ist jedoch ein sehr einfacher Ansatz.