Linq i deklaracja zapytania w polu klasy

0

Witam wszystkich.

Od niedawna uczę się linqu i jak do tej pory wystarczyły mi kursy i google by rozwiązać wszystkie moje wątpliwości. Niestety natrafiłem na problem z którym nie mogę sobie poradzić więc proszę was o pomoc. Nie będę omawiał całego mojego programu tylko dam mały przykład który obrazuje ten problem.

We wszystkich przykładach jakie do tej pory spotkałem pisząc zapytanie używa się vara. Jest to bardzo wygodne bo nie trzeba się zastanawiać jakiego typu jest zapytanie. Niestety w moim programie zapytanie musi być jako pole klasy, więc nie mogę użyć vara tylko muszę mu nadać konkretny typ. Problem jest w tym że nie wiem jaki typ mam nadać dla zapytania które jest poniżej.

class PrzykladowaKlasa
    {
        private nieznany_mi_typ zapytanie;

        public PrzykladowaKlasa()
        {
            XDocument xdokument = XDocument.Load(@"plikxml.xml");

            zapytanie = from wartosc in xdokument.Descendants("węzeł")
                        select new
                        {
                            pole1 = wartosc.Descendants("pole1").First().Value,
                            pole2 = wartosc.Descendants("pole2").First().Value,
                            pole3 = wartosc.Descendants("pole3").First().Value,
                            atrybut = wartosc.Attributes("atrybut").First().Value
                        };
        }

        public void JakasFunkcja()
        {
            //kod w którym wykorzystuje się "zapytanie"
        }
    }
0

najedź sobie na słowo kluczowe "var" w visual studio - tam jest podpowiedź jaki to typ

0

Przede wszystkim nie odczytuj plików w konstruktorze, bo konstruktor służy do tworzenia obiektu, a nie wykonywania operacji I/O.
A po drugie, z tego co widzę, to tworzysz obiekt typu anonimowego, więc nie będziesz miał jego nazwy na etapie pisania kodu źródłowego.

Utwórz sobie klasę, zrób pole typu tej klasy, a dane z pliku odczytaj w jakiejś metodzie wywołanej z zewnątrz.

1

Nie możesz zadeklarować typu anonimowego jako pole klasy. Z msdn:

http://msdn.microsoft.com/en-us/library/bb397696.aspx napisał(a)

You cannot declare a field, a property, an event, or the return type of a method as having an anonymous type. Similarly, you cannot declare a formal parameter of a method, property, constructor, or indexer as having an anonymous type.

var możesz używać tylko lokalnie.
Jeżeli potrzebujesz wyniku jako pole klasy, to powinieneś użyć odpowiedniego typu:

class QueryResult
{
   public string pole1,pole2,pole3,....,pole13100400;
   public string atrybut;
}
/*****/
zapytanie = from wartosc in xdokument.Descendants("węzeł")
                        select new QueryResult()
                        {
                            pole1 = wartosc.Descendants("pole1").First().Value,
                            pole2 = wartosc.Descendants("pole2").First().Value,
                            pole3 = wartosc.Descendants("pole3").First().Value,
                            atrybut = wartosc.Attributes("atrybut").First().Value
                        };

zapytanie może być tutaj spokojnie polem klasy. Oczywiście jest typu QueryResult.

0
pole1 = wartosc.Descendants("pole1").First().Value,

to zdaje się zwraca stringa, czy da się tak bezpośrednio wyselectować w pole typu int bez rzutowania?

0

Minęło już trochę czasu od założenia przeze mnie tego tematu, jednak nie miałem czasu by w środku tygodnia skorzystać z waszych rad. Jednak nastał weekend więc mogę się podzielić do czego doszedłem. Pomoc Sarrusa naprowadziła mnie na rozwiązanie problemu, poszperałem jeszcze w Google i udało mi się napisać poprawny kod. Umieszczam go tutaj by inni nie musieli się męczyć tak jak ja.

    class PrzykladowaKlasa
    {
        private class QueryResult
        {
            public string pole1, pole2, pole3;
            public string atrybut;
        }
        
        private IEnumerable<QueryResult> zapytanie;
        
        public PrzykladowaKlasa()
        {
            XDocument xdokument = XDocument.Load(@"plikxml.xml");
            zapytanie = from wartosc in xdokument.Descendants("węzeł")
                         select new QueryResult
                         {
                             pole1 = wartosc.Descendants("pole1").First().Value,
                             pole2 = wartosc.Descendants("pole2").First().Value,
                             pole3 = wartosc.Descendants("pole3").First().Value,
                             atrybut = wartosc.Attributes("atrybut").First().Value
                         };
        }
 
        public void JakasFunkcja()
        {
            foreach (var a in zapytanie)
                MessageBox.Show(a.atrybut);            
        }
    }
somekind napisał(a):

Przede wszystkim nie odczytuj plików w konstruktorze, bo konstruktor służy do tworzenia obiektu, a nie wykonywania operacji I/O.
Wiem, że się nie odczytuje i normalnie tego tak nie robię. Powyższy przykład miał tylko pokazać z jakim problemem się borykam więc nie martwiłem się innymi "zbędnymi" rzeczami np. tym, że próba wczytania nie istniejącego pliku w konstruktorze może wywalić program.

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