Bagikan melalui


Modifikasi pohon XML dalam memori vs konstruksi fungsional (LINQ ke XML)

Memodifikasi pohon XML di tempat adalah pendekatan tradisional untuk mengubah bentuk dokumen XML. Aplikasi umum memuat dokumen ke dalam penyimpanan data seperti DOM atau LINQ ke XML; menggunakan antarmuka pemrograman untuk menyisipkan atau menghapus simpul, atau mengubah kontennya; lalu menyimpan XML ke file atau mengirimkannya melalui jaringan.

LINQ ke XML memungkinkan pendekatan lain yang berguna dalam banyak skenario: konstruksi fungsional. Konstruksi fungsional memperlakukan memodifikasi data sebagai masalah transformasi, bukan sebagai manipulasi terperinci dari penyimpanan data. Jika Anda dapat mengambil representasi data dan mengubahnya secara efisien dari satu bentuk ke bentuk lain, hasilnya sama seperti jika Anda mengambil satu penyimpanan data dan memanipulasinya dalam beberapa cara untuk mengambil bentuk lain. Kunci pendekatan konstruksi fungsional adalah meneruskan hasil kueri ke XDocument dan XElement konstruktor.

Dalam banyak kasus, Anda dapat menulis kode transformasional dalam sepersekian waktu yang diperlukan untuk memanipulasi penyimpanan data, dan kode yang dihasilkan lebih kuat dan lebih mudah dipertahankan. Dalam kasus ini, meskipun pendekatan transformasian dapat membutuhkan lebih banyak daya pemrosesan, ini adalah cara yang lebih efektif untuk memodifikasi data. Jika pengembang terbiasa dengan pendekatan fungsional, kode yang dihasilkan dalam banyak kasus lebih mudah dipahami, dan mudah untuk menemukan kode yang memodifikasi setiap bagian pohon.

Pendekatan di mana Anda memodifikasi pohon XML di tempat lebih akrab bagi banyak pemrogram DOM, sedangkan kode yang ditulis menggunakan pendekatan fungsional bisa terlihat tidak dikenal oleh pengembang yang belum memahami pendekatan tersebut. Jika Anda hanya perlu melakukan modifikasi kecil pada pohon XML besar, pendekatan di mana Anda memodifikasi pohon di tempat dalam banyak kasus akan memakan waktu CPU yang lebih sedikit.

Artikel ini menyediakan contoh kedua pendekatan. Misalkan Anda ingin mengubah dokumen XML sederhana berikut sehingga atribut menjadi elemen:

<?xml version="1.0" encoding="utf-8" ?>
<Root Data1="123" Data2="456">
  <Child1>Content</Child1>
</Root>

Contoh pertama dari berikut menggunakan pendekatan modifikasi tradisional di tempat, dan yang kedua menggunakan pendekatan konstruksi fungsional.

Contoh: Mengubah atribut menjadi elemen dengan pendekatan tradisional di tempat

Anda dapat menulis beberapa kode prosedural untuk membuat elemen dari atribut, lalu menghapus atribut, sebagai berikut:

XElement root = XElement.Load("Data.xml");
foreach (XAttribute att in root.Attributes()) {
    root.Add(new XElement(att.Name, (string)att));
}
root.Attributes().Remove();
Console.WriteLine(root);
Dim root As XElement = XElement.Load("Data.xml")
For Each att As XAttribute In root.Attributes()
    root.Add(New XElement(att.Name, att.Value))
Next
root.Attributes().Remove()
Console.WriteLine(root)

Contoh ini menghasilkan output berikut:

<Root>
  <Child1>Content</Child1>
  <Data1>123</Data1>
  <Data2>456</Data2>
</Root>

Contoh: Mengubah atribut menjadi elemen dengan pendekatan konstruksi fungsi

Sebaliknya, pendekatan fungsional terdiri dari kode untuk membentuk pohon baru, memilih dan memilih elemen dan atribut dari pohon sumber, dan mengubahnya sebagaimana mestinya saat ditambahkan ke pohon baru.

XElement root = XElement.Load("Data.xml");
XElement newTree = new XElement("Root",
    root.Element("Child1"),
    from att in root.Attributes()
    select new XElement(att.Name, (string)att)
);
Console.WriteLine(newTree);
Dim root As XElement = XElement.Load("Data.xml")
Dim newTree As XElement = _
    <Root>
        <%= root.<Child1> %>
        <%= From att In root.Attributes() _
            Select New XElement(att.Name, att.Value) %>
    </Root>
Console.WriteLine(newTree)

Contoh ini menghasilkan XML yang sama dengan contoh pertama. Namun, perhatikan bahwa Anda benar-benar dapat melihat struktur XML baru yang dihasilkan dalam pendekatan fungsi. Anda dapat melihat pembuatan Root elemen, kode yang menarik Child1 elemen dari pohon sumber, dan kode yang mengubah atribut dari pohon sumber menjadi elemen di pohon baru.

Contoh fungsi dalam hal ini tidak lebih pendek atau lebih sederhana daripada contoh pertama. Namun, jika Anda memiliki banyak perubahan untuk dilakukan pada pohon XML, pendekatan prosedural akan menjadi cukup kompleks dan agak obtuse. Sebaliknya, saat menggunakan pendekatan fungsi, Anda masih hanya membentuk XML yang diinginkan, menyematkan kueri dan ekspresi yang sesuai, untuk menarik konten yang diinginkan. Pendekatan fungsi ini menghasilkan kode yang lebih mudah dipertahankan.

Perhatikan bahwa dalam hal ini pendekatan fungsional mungkin tidak akan melakukan cukup serta pendekatan manipulasi pohon. Masalah utamanya adalah bahwa pendekatan fungsi ini membuat lebih banyak objek berumur pendek. Namun, tradeoff adalah yang efektif jika menggunakan pendekatan fungsional memungkinkan produktivitas programmer yang lebih besar.

Ini adalah contoh yang sangat sederhana, tetapi berfungsi untuk menunjukkan perbedaan filosofi antara kedua pendekatan. Pendekatan fungsi ini menghasilkan keuntungan produktivitas yang lebih besar untuk mengubah dokumen XML yang lebih besar.