C# Linq/XML - wczytywanie dzieci do listy

0

Tworzę obecnie parser plików XML w C#. Fragment wczytywanego pliku wygląda następująco:

 <listaPOI>
    <POI>
      <id>1</id>
      <nazwa>Nowa nazwa punktu 1</nazwa>
      <ikona>sciezka wzgledna do ikony</ikona>
      <wsp>
        <szer>71</szer>
        <dl>51</dl>
      </wsp>
      <adres>Adresy nowy</adres>
      <realizacja>2029</realizacja>
      <opis>Opis punktu zmieniamy</opis>
      <multimedia>
        <odnosnik1>odnosnik/do/pierwszego</odnosnik1>
        <odnosnik2>odnosnik/do/drugiego</odnosnik2>**
      </multimedia>
      <obserwacyjne>
          <pozycja1>
          <szer>72</szer>
          <dl>52</dl>
        </pozycja1>
        <pozycja2>
          <szer>73</szer>
          <dl>53</dl>
        </pozycja2>
      </obserwacyjne>
    </POI>

 

Mam napisaną aplikację okienkową, która odpowiednio wyświetla te dane. Moim problemem jest wczytanie danych z <odnosnik1>, <odnosnik2>, <pozycja1> ... do listy zawierającej obiekty typu string. Kod w C# jak na razie wygląda następująco:

 
// Wczytywanie  

var rezultat = from q in xDoc.Descendants("POI")//Descendants("POI")
                               where (q.Element("id").Value.Equals(L.Text)) // porownanie id kliknietego i wyszukanego
                               select new POI
                               {
                                   
                                   id = q.Element("id").Value,
                                   nazwa = q.Element("nazwa").Value,
                                   ikona = q.Element("ikona").Value,
                                   wspolrzedna = Tuple.Create(q.Element("wsp").Element("szer").Value, 
                                                              q.Element("wsp").Element("dl").Value
                                                             ),
                                   adres = q.Element("adres").Value,
                                   realizacja = q.Element("realizacja").Value,
                                   opis = q.Element("opis").Value,
                                   //multimedia = q.Element("multimedia").Elements("odnosnik").ToList();
                                   //multimedia = new string[] { q.Element("multimedia").Elements("odnosnik").Value }
                                   //obserwacyjne
                                   //przefiltrowanie i dodawanie elementów z list

                               };


// Klasa POI
 public class POI
    {
       
        public string id { set; get; }
        public string nazwa { get; set; }
        public string ikona { get; set; }
        public Tuple <string,string> wspolrzedna { get; set; }
        public string adres { get; set; }
        public string realizacja { get; set; }
        public string opis { get; set; }
        public List<string> multimedia { get; set; } // multimedia - same odnosniki
        public List<Tuple<string,string>> obserwacyjne { get; set; } // lista puinktow
    }

Proszę o pomoc jak napisać to podzapytanie.

0

spróbuj użyć tego:

    a.fridOpen = e.Element("Multimedia").Attribute("odnosnik1").Value;
0
ne0 napisał(a):

spróbuj użyć tego:

    a.fridOpen = e.Element("Multimedia").Attribute("odnosnik1").Value;

A możesz powiedzieć mi co oznacza a.fridOpen ? Zależy mi na pobraniu wszystkich odnośników, czyli coś jakby wciśnięcie tam pętli foreach.

1

zmienna do której zapisujesz wartość z XML, ten kawałek kodu jest wycięty z mojej aplikacji, "a" to obiekt który ma pole "fridOpen". Ty sobie możesz wstawić to gdzie chcesz. ja Ci podałem jak mam u siebie to zrobione. Skup się na e.Element oraz Attributes. Dzięki właśnie attributes "wchodzisz" do dzieci.

1

A czy to sam stworzyłeś strukturę tego xml-a czy jest narzucona? A konkretnie czemu są tam "odnosnik1", "odnosnik2" itd. i czemu "pozycja1", "pozycja2" itd.
Nie lepiej i prościej będzie "odnosnik", "pozycja" lub jeśli potrzebujesz mieć numeracje to <odnosnik value="1">, <pozycja value="2"> itd.?
A co do

 a.fridOpen = e.Element("Multimedia").Attribute("odnosnik1").Value;

Jest bez sensu ponieważ w tym xmlu "odnosnik1" nie jest atrybutem a elementem. Mało tego w tym xmlu nie ma ani jednego atrybutu. :)

EDIT: Dla xml takiego jak ja proponuje ( jest sensowniejszy według mnie ):

<?xml version="1.0" encoding="UTF-8"?>
<POI>
   <id>1</id>
   <nazwa>Nowa nazwa punktu 1</nazwa>
   <ikona>sciezka wzgledna do ikony</ikona>
   <wsp>
      <szer>71</szer>
      <dl>51</dl>
   </wsp>
   <adres>Adresy nowy</adres>
   <realizacja>2029</realizacja>
   <opis>Opis punktu zmieniamy</opis>
   <multimedia>
      <odnosnik value="1">odnosnik/do/pierwszego</odnosnik>
      <odnosnik value="2">odnosnik/do/drugiego</odnosnik>
   </multimedia>
   <obserwacyjne>
      <pozycja value="1">
         <szer>72</szer>
         <dl>52</dl>
      </pozycja>
      <pozycja value="2">
         <szer>73</szer>
         <dl>53</dl>
      </pozycja>
   </obserwacyjne>
</POI>

Dla twojej klasy zapytanie wyglądało by tak:

var result = from q in xDoc.Descendants("POI")
                      where (q.Element("id").Value.Equals(L.Text))
            select new POI
            {
               id = q.Element("id").Value,
               nazwa = q.Element("nazwa").Value,
               ikona = q.Element("ikona").Value,
               wspolrzedna = Tuple.Create(q.Element("wsp").Element("szer").Value,
                  q.Element("wsp").Element("dl").Value
                  ),
               adres = q.Element("adres").Value,
               realizacja = q.Element("realizacja").Value,
               opis = q.Element("opis").Value,

               multimedia = q.Element("multimedia").Elements("odnosnik").Select(x => x.Value).ToList(),
               obserwacyjne =
                  new List<Tuple<string, string>>(
                     q.Element("obserwacyjne")
                        .Elements("pozycja")
                        .Select(x => new Tuple<string, string>(x.Element("szer").Value, x.Element("dl").Value)))
            };

Oczywiście łatwiej by było użyć po prostu serializacji:
http://msdn.microsoft.com/en-us/library/90c86ass(v=vs.110).aspx

0

Dokładnie o to mi chodziło! Dzięki Tobie zaoszczędziłem dużo czasu :). Struktura XML'a nie jest do końca narzucona, będzie on wykorzystywany w pewnym projekcie. Szczerze mówiąc ta aplikacja to jedna z pierwszych rzeczy jaką piszę w C# - nawet nie wiedziałem co to jest serializacja, tylko szybko szukałem jakiś narzędzi w celu łatwego wczytania i obróbki XML'a, stąd natknąłem się na LINQ.
W wakacje postaram się wrzucić paskudne kody źródłowe tejże aplikacji, choćby tutaj. Dziękuje i pozdrawiam :)

1 użytkowników online, w tym zalogowanych: 0, gości: 1