3. Rnice pomidzy tablicami a kolekcjami: Tablica deklaruje typ
elementw, ktre przechowuje. Kolekcja tego nie robi poniewa kolekcja
przechowuje elementy jako obiekty. Tablica ma okrelony rozmiar i
nie mona jej powikszyd ani zmniejszyd. Kolekcja w zalenoci od
potrzebny dynamicznie dostosowuje automatycznie rozmiar. Tablica
moe byd wielowymiarowa. Kolekcja nie moe byd wielowymiarowa. Jednak
kolekcje mog przechowywad wewntrz siebie inne kolekcje.
4. Kolekcja ArrayList ArrayList mona traktowad jak ulepszenie
tablicy. Jeli irytoway ci pewne wady tablicy, to ta klasa wikszod
ich rozwie . Potrafi ona: Usuwad wybrane elementy z kolekcji przy
uyciu metody Remove(). Elementy automatycznie ustawi si w wybrane
miejsca. Za pomoc metody RemoveAt() usuwa si dany element przy
pomocy jego indeksu. Dodawad kolejne nowe elementy za pomoc metody
Add(). W razie potrzeby ArrayList automatycznie zmieni swj rozmiar.
Dodawad elementy w rodku zbioru elementw za pomoc metody "Insert().
Moe odnied referencyjnie do istniejcego elementu w ArrayList za
pomoc nawiasw kwadratowych i numery indeksu elementu.
5. ArrayList liczby = new ArrayList(); //przykad meotdy Add for
(int i = 0; i < 10; i++) { liczby.Add(i); } //Przykad metody
Remove() int usuneL = 1; liczby.Remove(usuneL); //Przykad metody
RemoveAt() liczby.RemoveAt(7); //Przykad Insert() int dodamL = 121;
l iczby.Insert(3, dodamL);
6. Jak widzisz kasowanie i dodawanie elementw nie stworzyo
baaganu w ArrayList. ArrayList posiada jeszcze wiele innych fajnych
moliwoci, jak kasowanie elementw od - do za pomoc RemoveRange().
Wyszukiwanie indeksu wybranego elementu za pomoc IndexOf(). Czy
czyszczenie zawartoci za pomoc metody Clear(). oraz moliwod
kopiowania zawartoci do tablicy obiektw za pomoc metody ToArray().
Musz to byd obiekty poniewa ArrayList tak przechowuje elementy bez
okrelenia ich typw. Czyli ArrayList moe przechowywad wiele rnych
elementw.
7. int poszukiwany = 9; int indeks =
liczby.IndexOf(poszukiwany); liczby.RemoveRange(0, 4); object[]
tablicaObiektw = liczby.ToArray(); liczby.Clear(); int wielkosc =
liczby.Count;
8. DEMO
9. Kolekcje generyczne
10. Kolekcje Typ object referuje si do wartoci o jakimkolwiek
typie. Wszystkie typy referencyjne dziedzicz automatycznie po
klasie System.Object take wbudowane klasy w .NET . Daje to moliwod
tworzenia metod czy zmiennych, ktre mog przechowywad rne wartoci.
Klasy takie jak ArrayList, HashTable s kolekcjami, ktre mog
przechowywad wszystko. Opisaem je w tym wpisie. Moesz tworzyd
kolejki, stosy, ktre mog zawierad w sobie kady typ. Problem polega
na tym, e skoro te kolekcje mog przechowywad wszystko to mog w nich
znaled si nieodpowiednie obiekty. Co prawda mamy do dyspozycji sowa
kluczowe jak as czy is , ktre mog sprawdzad czym tak naprawd jest
dany object , ale wci nie zmienia to faktu, e jest to uciliwe.
Kolejn powan wad tego zastosowania jest pakowanie i wypakowywanie
danych. Umieszczajc np. liczb do ArrayList musi byd ona spakowana
do obiektu , a gdy chcemy j wycignd musi byd ona wypakowywana.
11. int zlo = 42; ArrayList al = new ArrayList(); al.Add(zlo);
//pakowanie zlo = (int)al[0] + 1; //wypakowywanie
12. int zlo = 42; Queue kolejka = new Queue();
kolejka.Enqueue(zlo); //wrzucanie do kolejki zlo =
(int)kolejka.Dequeue(); //wyciganie z kolejki
13. DYRASTYCZNY PRZYKAD
14. class Kobieta { public void Zabawa(FacetJohnyBrawo facet) {
Console.WriteLine("Dobrze si bawiam"); } }
15. class FacetJohnyBrawo { ArrayList mojekobiety = new
ArrayList(); public void DodajKobiete(Kobieta kobieta) {
mojekobiety.Add(kobieta); } public void IdzNaRandkePoKoleji() {
foreach (var kobieta in mojekobiety) { Console.WriteLine(kobieta);
} } }
17. class FacetJohnyBrawo { List mojekobiety = new List();
public void DodajKobiete(Kobieta kobieta) {
mojekobiety.Add(kobieta); } public void IdzNaRandkePoKoleji() {
foreach (var kobieta in mojekobiety) { kobieta.Zabawa(this); } }
}
18. O CO CHODZI
19. int dobro = 0; Queue kolejka = new Queue();
kolejka.Enqueue(dobro); dobro = kolejka.Dequeue();
20. public class Queue : //...public class Stack : //... public
void Enqueue(T item); public T Dequeue();
21. T Parametr T zastpuje dany typ i jest zastpiony prawdziwym
typem w czasie deklaracji danej klasy Generics. Do tych klas nie
mona wic ju umiecid innych typw od tych, ktre zadeklarowalimy
zamiast . Mechanizm T jest bardziej skomplikowany ni si wydaje.
Jego dziaanie nie polega dosownie na zastpieniu tego elementu jakby
kod to by jaki notatnik, czy word. Kompilator dokonuje dokadn i
kompletn substytucje w taki sposb ,aby T mogo referowad si do
kadego typu. Jednak przykadowo Queue i Queue powinny byd traktowane
jak dwa oddzielne typy danych. Specyficzne typy klas Generics
nazywane s zbudowanymi typami constructed types .
22. DEMO
23. Delegaty
24. Wstp W WPF mamy do dyspozycji kontrolki , jak przyciski czy
textbox-y. Kiedy klikasz na przycisk, czy piszesz jaki tekst
oczekujesz , e dane zdarzenie wykona si natychmiastowo. W
rzeczywistoci tak nie jest. Aplikacja musi si na chwile zatrzymad i
odpowiednio przekierowad dziaania uytkownika. Nie dotycz to tylko
aplikacji z interfejsem uytkownika (UI) ,ale do kadej innej
aplikacji, w ktrej czynnod X musi byd wykonana natychmiastowo bez
wzgldu na inne procesy w tle.
25. Delegata jest wskanikiem do danej metody. Poprzez dan
delegate moesz wywoad dan metod. Kiedy wywoujesz dan delegat
program tak naprawd wykonuje dan metod, do ktrej delegata si
referowaa.
26. C++ Jeli znasz jzyk programowania taki jak C++ to zapewne
zdae sobie ju spraw , e delegata dziaa podobnie do wskanika
funkcji. Jednak delegaty s bezpieczniejsze, dana delegata moe tylko
referowad si do metody, ktrej sygnatura jest zgodna z delegat. Nie
moesz wywoad delegaty, ktra nie referuje si do waciwiej dla siebie
metody
27. Problem ze zrozumieniem Znajc ycie, poniewa sam miaem z tym
problem, na pewno si teraz zastanawiasz, po co w ogle s delegaty?
Jeli chc wywoad metod X to j wywouj po co mi delegata, ktra robi
dokadnie to samo tylko pozwala wywoad metod pod inn nazw. Czas na
przykad.
28. Sytuacja Mamy dziecko i oboje rodzicw. Dziecko pacze i
trzeba je przewind. Poniewa matka jest zajta deleguje to zadanie
ojcu. A ojciec ma w swojej klasie metod, ktr zadnie to moe wykonad.
Bez delegat przykad wyglda tak.
29. class Dziecko { private bool glodny;//tak rodzice nie wiedz
co chce dziecko :) private Mama mama; private Tata tata; public
void MozeChceJesc() { if (glodny == false) {
Console.WriteLine("Dziecko nie jest godne"); } else { if
(mama.zmczona == false) { mama.Nakarmienie(this); } else {
tata.Nakarmienie(this); } glodny = false; } } //a ty mylae ,e
dzieci bior si z pszczek i kwiatkw public Dziecko(Mama
duzaCieplaPlama, Tata duzaZnajomaPlama) { //z puntu nowonarodzonego
dziecka wszystko jest jedn fajn plam mama = duzaCieplaPlama; tata =
duzaZnajomaPlama; } }
30. Opis cz1 Zakadamy ,e wszystkie obowizki wykonuje zawsze
mama ,ale jeli jest ona zmczona to obowizek przechodzi na ojca ,a
ojciec nie moe byd zmczony. Poniewa rodzice nie wiedz, co dziecko
chce , jego pola jak godny s prywatne i nie maj waciwoci
przypisanych do nich.
31. Opis cz2 Istnieje jednak duo wikszy problem. Te rozwizanie
nie jest elastyczne. Gdyby nagle si okazao si, e babcia i dziadek
te mog zajmowad si tymi obowizkami musiabym dodad ich do klasy
Dziecko. Jednym sowem obecne rozwizane jest stworzone do jednego
konkretnego rozwizania.
32. Co naley zrobi T logik wypadao jako oddzielid od klasy
dziecko. Dlatego stworzenie abstrakcyjnej klasy bazowej
OpiekunDziecka te tutaj do kooca nie rozwie sprawy. W programowaniu
nie jest to sympatycznie odbierane zwaszcza jeli programista
spodziewa si , e ten kod moe ulec zmianie. W pracach domowych na
studiach moesz sobie na to pozwolid ale nie w yciu.
33. UYWANIE DELEGAT
34. Co naley zrobi Mimo, i metody maj rne nazwy i mog pochodzid
od rnych klas wszystkie musz mied podobny ksztat. W tym przykadzie
kada z metod przyjmuje parametr klasy Dziecko i nie zwraca adnej
wartoci. Format wszystkich tych metod bdzie nastpujcy. void
Nazwa(Dziecko dziecko)
35. delegate void MozeChceJescDelgata(Dziecko dziecko); Na co
trzeba zwrcid uwag: Uycie sowa kluczowego delegate przy deklaracji
delegaty Delegata definiuje ksztaty metody, do ktre si referuje.
Metoda nie moe niczego zwracad void i musi przyjmowad jeden
parametr dziecko.
36. Po stworzeniu delegaty moesz stworzyd jej instancje. Przy
uyciu operatora += moesz przypisad do niego odpowiedni metod. Zrobi
to w konstruktorze klasy Dziecko ,aby nie wnikad na razie w szczegy
sytuacyjne. Mam przecie wyjanid jak dziaaj delegaty. class Dziecko
{ delegate void mozeChceJescDelgata(Dziecko dziecko); private
mozeChceJescDelgata mozeChceJesc; // instancja delegaty public
Dziecko(Mama mama) { this.mozeChceJesc += mama.Nakarmienie; }
}
37. Dodanie metod do delegat Dodajesz metod do delegaty w tym
momencie metoda nie jest wywoywana. Operator =+ dla delegaty jest
nadpisany i ma swoje unikalne zastosowanie. Zauwa te , e do metody
nie dodaem adnego parametru i nie ma nawet nawiasw (). Istnieje
jeszcze inny sposb na przypisanie delegaty do odpowiedniej metody
jednak wyraenie += jest bezpieczniejsze w uyciu oraz inicjacja
przebiegnie automatycznie. Ten inny sposb wyglda tak.
38. this.mozeChceJesc = new
mozeChceJescDelgata(mama.Nakarmienie); Jak widzisz ilod kodu jest
troch wiksza ale w ten sposb instancja delegaty bdzie zawsze
odwoywad si do jednej metody. Uywajc znaku += tak naprawd dodajesz
nastpne moliwe metody, ktre maj si wykonad
39. Uwaga Wywoanie delgaty, ktra nie jest zainicjowana oraz nie
ma przypisanej adnej metody grozi wyrzuceniem wyjtku
NullReferenceException.
40. Przykad CDN Tak jak powiedziaem wczeniej uywajc wyraenia +=
skutkuje przypisaniem kolejnej metody do danej delegaty. Jest to
zwykle zaleta ni wada. Dlaczego? Ot wyobra sobie tak sytuacje.
Skoro rodzice nie wiedz, co chce dziecko, to najczciej wykonuj
wszystkie operacje po kolei. Przynajmniej tak to wyglda z
programistycznego punktu widzenia poniewa obiekty mama i tata nie
posiadaj sztucznej inteligencji aby zgadywad precyzyjnie co chce
dziecko xD.
41. class Dziecko { delegate void cosChceDelgata(Dziecko
dziecko); private cosChceDelgata cosChce; // instancja delegaty
public Dziecko(Mama mama) { this.cosChce += mama.Przewiniecie;
this.cosChce += mama.Nakarmienie; this.cosChce += mama.Ululanie; }
public void CosChceMetoda() { this.cosChce(this); } }
42. Dziecko Rosesmary = new Dziecko(new Mama());
Rosesmary.CosChce();
43. Mocna strona delegat To bardzo mocna strona delegaty
wszystkie metody wykonay si i to w okrelonej kolejnoci. W koocu
wolabym przypisad 100 metod do jednej delegaty, ni pisad 100
linijek za kadym razem, gdy chc wykonywad te operacje. Delegaty te
daj pewn elastycznod bo przecie kolejnod dziaao bya zadeklarowana w
konstruktorze, a nie bezporednio w kodzie jakbym pisa metoda po
metodzie.
44. Moesz te usuwad metody za pomoc operatora =. this.cosChce
-= mama.Nakarmienie;
45. Publiczne Delegaty Obecnie opiekunowie dziecka byliby
dodawani w konstruktorze poniewa obecnie instancja delegaty jest
prywatna. Warto j zmienid na publiczn w ten sposb klasa dziecko
powinna byd niezalena od swoich opiekunw
46. public cosChceDelgata cosChce; // instancja delegaty
47. delegate void cosChceDelgata(Dziecko dziecko); private
cosChceDelgata _cosChce; // instancja delegaty public
cosChceDelgata CosChce { get { return cosChce; } set { cosChce =
value; } }
48. Heremtyzacja dziecka Mona te zaszaled i dad klasie Dziecko
pene hermetyczne rozwizanie zakadajc nawet , e dziecko nie wie co
rodzice bd robid by zaspokoid jego potrzeby. Biedny dzieciak nawet
nie wie, co mu dolega i kiedy to przechodzi. Zasada hermetyzacji
jest taka brutalna.
49. public delegate void cosChceDelgata(Dziecko dziecko);
private cosChceDelgata cosChce; // instancja delegaty public void
Dodaj(cosChceDelgata MetodaX) { this.cosChce += MetodaX; } public
void Usun(cosChceDelgata MetodX) { this.cosChce -= MetodX; }
50. Wyraenia Lambda
51. class MaszynaPracujaca { public void UruchomMaszyne() {
Console.WriteLine("Maszyna Uruchomiona"); } public void
ObliczWzorZimnejFuzji() { Console.WriteLine("Obliczyem wzr na zimn
fuzje: X^6 + Lin(3) * G"); } public void OdnajdzSensZycia() {
Console.WriteLine("42"); } public void WylaczMaszyne(int
czasZamkniecta) { Console.WriteLine("Zamkniecie za {0}",
czasZamkniecta); } }
52. class MaszynaZadan { public delegate void
listZadanDelegata(); private listZadanDelegata listaZadan; public
MaszynaZadan(MaszynaPracujaca maszyna) { listaZadan +=
maszyna.UruchomMaszyne; listaZadan +=
maszyna.ObliczWzorZimnejFuzji; listaZadan +=
maszyna.OdnajdzSensZycia; } public void RozpocznijZadania() {
listaZadan(); } }
53. MaszynaZadan mz = new MaszynaZadan(new MaszynaPracujaca());
mz.RozpocznijZadania(); Jak dobrze pamitasz mwiem te co o zasadzie
hermetyzacji czyli klasa MaszynaZadan jest chwilowo le napisana
poniewa jej dziaanie jest zalene od klasy MaszynaPracujca. Problem
ten mona rozwizad w nastpujcy sposb. Sprawiajc , e klasa
MaszynaZadan moe byd elastycznie dostosowywana.
54. class MaszynaZadan { public delegate void
listZadanDelegata(); private listZadanDelegata listaZadan; public
void Dodaj(listZadanDelegata MetodaX) { listaZadan += MetodaX; }
public void Usun(listZadanDelegata MetodX) { listaZadan -= MetodX;
} public void RozpocznijZadania() { if (listaZadan != null)
listaZadan(); } }
55. ADAPTERY Moe nie zauwaae ,ale w klasie MaszynaPracujca jest
metoda WylaczMaszyne.
56. class MaszynaPracujaca { public void UruchomMaszyne() {
Console.WriteLine("Maszyna Uruchomiona"); } public void
ObliczWzorZimnejFuzji() { Console.WriteLine("Obliczyem wzr na zimn
fuzje: X^6 + Lin(3) * G"); } public void OdnajdzSensZycia() {
Console.WriteLine("42"); } public void WylaczMaszyne(int
czasZamkniecta) { Console.WriteLine("Zamkniecie za {0}",
czasZamkniecta); } }
57. Metoda ta przyjmuje parametr int czyli jej ksztat bd jak
wolisz sygnatura jest inna ni innych metod tej klasy. Ten ksztat
jest nie zgodny z sygnatur delegaty, ktra przyjmuje tylko metody
bezparametrowe.
58. class MaszynaPracujaca { public void UruchomMaszyne() {
Console.WriteLine("Maszyna Uruchomiona"); } public void
ObliczWzorZimnejFuzji() { Console.WriteLine("Obliczyem wzr na zimn
fuzje: X^6 + Lin(3) * G"); } public void OdnajdzSensZycia() {
Console.WriteLine("42"); } public void WylaczMaszyne(int
czasZamkniecta) { Console.WriteLine("Zamkniecie za {0}",
czasZamkniecta); } public void NatchmiastoweWylaczenie() {
this.WylaczMaszyne(0); } }
59. mz.Dodaj(mp.NatchmiastoweWylaczenie); //dla klasy ktra jest
w wersji konstruktora listaZadan +=
maszyna.NatchmiastoweWylaczenie;
60. Wyraenie Lambda Oczywicie pojawio si pytanie gdzie ta
metoda adaptujca powinna byd. Oczywicie jest ona w klasie
MaszynaPracujca std to sowo kluczowe this jako wskazwka. Jednak co
jeli nie moemy zmienid zawartoci tej klasy. Nawet jeli moemy
zmienid zawartod tej klasy, to co jeli ta klasa jest gigantyczna.
Tak czy siak, ta metoda istnieje tylko z powodu jednej delegaty i
raczej na pewno nie bdzie uywana nigdzie indziej. W C# do takich
przypadkw lepiej zastosowad wyraenie lambda czyli nasz gwiazd tego
wykadu.
61. Wyraenie Lambda Wyraenie lambda zwraca metod. Brzmi to
fantastycznie chocia na pewno moesz si zastanawiad jako to w ogle
dziaa. Zwykle wyraenia w C# zwracaj jak wartod X. W jzykach
programowania funkcjonalnego jest to dod czsto spotykane
zachowanie. Wraz z C# 3.0 pojawiy si wyraenia lambda (jak i
zapytania LINQ) i od tamtej pory twj kod miejscami moe przypominad
jzyk funkcjonalny.
62. Programowanie funcjonalne Oto maa informacja z Wikipedii z
nagwka Functional programming in non-functional languagesw wpise o
jzykach programowania funkcjonalnego. Jak widzisz pewne trendy
przechodz nawet na jzyki programowania, ktre nie s funkcjonale i
nie mwi si tu tylko o C#. Doszo to nawet do jzyka PHP, heno tego
bym si nie spodziewa. Kiedy nie by to obiektowy jzyk. Z tego co
kiedy czytaem w kolejnej wersji jzyka Java te maj pojawid si te
wyraenia.Wyraenia lambda s nawet obecne we wzorcach
projektowych.
63. Tworzenie metod Koniec jednak tej lektury. Wyraenie lambda
nie jest takie skomplikowane. To tylko kolejny zestaw znakw, ktre
trzeba zapamitad i tyle. Zreszt jest ono bardzo uyteczne , a wic
okazja uycia pojawi si jeszcze nie raz. Typowa metoda musi skadad
si z 4 elementw: Nazwy Listy parametrw Ciaa metody Zwracanej
wartoci
64. Wyraenie Lambda Wyraenie lambda zawiera tylko dwa elementy:
list parametrw oraz ciao metody. Wyraenia Lambda nie okrelaj swojej
nazwy. Wyraenie lambda nie definiuje te zwrotnego parametru. Jednak
jaki parametr moe byd zwracany jeli wynika to z zawartoci jej ciaa.
Wracajc do problemu z metod WyaczMaszyne(int czasZamkniecia) .
Musimy stworzyd adapter metody WylaczMaszyne w taki sposb ,aby nie
miaa ona adnych parametrw i mogaby byd dodana do instancji delegaty
ListaZadan.
65. mz.Dodaj( (() => { mp.WylaczMaszyne(0);}) ); //dla klasy
ktra jest w wersji konstruktora listaZadan += (() => {
maszyna.WylaczMaszyne(0); });
66. WYRAENIE LAMBDA CHCE WICEJWICEJ FORM
67. DEMO
68. Lambda podsumowanie Czas na podsumowanie tego kodu i to nie
za pomoc zielonego komentarza w kodzie. Wyraenia lambda mog zwracad
wartoci jednak musz one pasowad do typu danej delegaty, do ktrej s
dodawane. Ciao wyraenia lambda moe byd prostym wyraeniem albo
blokiem kodu C# z wieloma stwierdzeniami, wezwaniami innych metod,
definicj zmiennych i innych rzeczy. Zmienne zdefiniowane wewntrz
wyraenia lambda istniej tylko w tym bloku kodu i znikaj gdy metoda
si skooczy,
69. Lambda podsumowanie Wyraenie lambda ma dostp do wszystkich
zmiennych i metod znajdujcych si po za tym wyraeniem. W czasie
wykonywania wyraenia zmienne ulegaj zmianie tymczasowo. Warto o tym
pamitad. Jeli wyraenie lambda pobiera jakie parametry moesz nie
podawad ich typw poniewa kompilator skojarzy je z kontekstu danego
wyraenia. Jednak przy sowach kluczowych jak ref i out musisz te
podad ich typ. Wyraenie lambda moe zmienid wartoci na zawsze jeli s
one przesane do metody za pomoc sw kluczowych ref i out.
70. METODY ANONIMOWE
71. Metody Anonimowe W C# 2.0 czyli przed wyraeniami lambda byy
metody anonimowe, ktre speniay podobny cel do wyraeo lambda ale nie
byy tak elastyczne. Anonimowe metody zostay dodane po to aby dad
programistom moliwod definiowania delegat bez okrelenia ich nazw.
Metody te zawieray w sobie tylko swoj definicj.
73. Aby stworzyd metod anonimow musisz uyd sowa kluczowego
delegate. Parametry te musz byd okrelone w nawiasach przy sowie
kluczowym delegate. operacjeMatDwuArg += delegate(int x, int y) {
return x - y; };
74. Metody Anonimowe Zostay jednak one osunite w cieo. Zoone
zadania wygldaj o wiele lepiej w wyraeniu lambda dlatego te ju
prawie nikt nie pamita o tamtej formie zapisu. Chyba ,e kto z
jakiego powodu musi programowad w C# 2.0. To taka ciekawostka
poniewa wyraenia lambda s lepsze. Moe jednak kiedy spotkasz si z
takimi zapisami.
75. Piszemy zdarzenia
76. Wstp Jednak to jeszcze nie koniec. Co prawda moesz wywoad
wiele metod nie bezporednio za pomoc delegaty, ale wci musisz j
wywoad jawnie. Z programistycznego punktu widzenia dobrze byoby ,
aby delegaty uruchomiay si automatycznie gdy co wanego si wydarzy.
Przykadowo, w przypadku przegrzewania si reaktora atomowego wywoad
odpowiedni delegate, ktra wykona wszystkie metody po kolei w celu
jego wyczenia . W wielu wypadkach klasy znajdujce si w .NET pokazuj
uycie zdarzeo (event). Zdarzenia s uywane do zdefiniowania i
przechwytywania okrelonych akcji .Okrelaj one te uycie odpowiedniej
delegaty, ktra sobie z dan sytuacj X poradzi.Wikszod kontrolek z
WPF ,Windows Forms, Silverlight , a nawet z ASP.NET uywa zdarzeo.
Nawet np. sama klasa okna gwnego w WPF przechowuje nastpujce
zdarzenia.
77. Zdarzenia Zdarzenie moe byd zadeklarowane tylko w klasie i
to ona jest zawsze rdem tego zdarzenia. rdem danego zdarzenia jest
zazwyczaj klasa, ktra monitoruje dane rodowisko oraz wywouje
zdarzenie w momencie spenienia danego warunku. Niektre klasy maj
np. zdarzenia, ktre zostan wywoane w przypadku zajcia bdu. Idc tym
tropem przyszed mi gowy nastpujcy przykad zastosowania zdarzenia.
Mamy do dyspozycji klas PobieraczPlikw , ktrej zadaniem jest
pobranie poprzez sied rnego rodzaju plikw.
78. Zdarzenia Klasa ta ma dwa pola liczbeDoPobraniaPlikw, ktra
bdzie mwid nam ile plikw ma ta klasa pobrad. liczbePobranychPlikow
, ktra bdzie opisywad ile plikw zostao ju pobranych.
79. Zdarzenie PrzyBledziePobierania zajdzie jeli klasa wykryje
, e dane pobieranie nie skooczyo si prawidowo. Inne zdarzenie
SkonczonePobieranie zajdzie gdy liczba pobranych plikw bdzie rwna
liczbie plikw, ktr planowalimy pobrad. Zdarzenia te bd przechowywad
list metod, ktre maj byd wywoywane w czasie ich zajcia. Te metody s
nazywane subscribers , co dosownie mona przetumaczyd jako wyraz
subskryptami. Jednak na pewno nie jest to prawidowe tumaczenie (nie
ma takiego sowa w jzyku polskim). Metody te obsu nasze zdarzenie i
wykonaj odpowiednie akcje np. przy PrzyBledziePobierania uytkownik
zostanie poinformowany , e dany plik nie mg zostad pobrany.
80. event NazwaTypuDelegaty NazwaZdarzenia
81. class PobieraczPlikow { public delegate void
BladPobierniaDelegata(string wiadomosc); public delegate void
SkonczonePobieranieDelegata(); private int liczbaPobranychPlikow;
private int liczbaDoPobraniaPlikow; }
82. class PobieraczPlikow { public delegate void
BladPobierniaDelegata(string wiadomosc); public event
BladPobierniaDelegata PrzyBlendziePobierania; public delegate void
SkonczonePobieranieDelegata(); public event
SkonczonePobieranieDelegata SkonczonePobieranie; private int
liczbaPobranychPlikow; private int liczbaDoPobraniaPlikow; }
83. WYWOANIE ZDARZENIA
84. class PobieraczPlikow { public void WystapilBlad() { if
(PrzyBlendziePobierania != null) { PrzyBlendziePobierania("Wystapi
bd"); }
85. Jak widzisz jeli dana delegata w zdarzeniu definiuje jakie
parametry musz one byd podane w trakcie ich wywoania. Zdarzenia te
maj pewn istotn wbudowan funkcje mog one byd wywoane wewntrz klasy,
ktra je definiuje w tym wypadku wewntrz klasy PobieraczPlikow. Prba
wywoania zdarzenia poza t klas skooczy si bdem w czasie kompilacji
programu.
86. class PobieraczPlikow { //konstruktor public
PobieraczPlikow(int l) { liczbaDoPobraniaPlikow = l; } //proste
wywoanie zdarzenia public void WystapilBlad() { if
(PrzyBlendziePobierania != null) PrzyBlendziePobierania("Wystapi
bd"); } public delegate void BladPobierniaDelegata(string
wiadomosc); public event BladPobierniaDelegata
PrzyBlendziePobierania; public delegate void
SkonczonePobieranieDelegata(); public event
SkonczonePobieranieDelegata SkonczonePobieranie; private int
liczbaPobranychPlikow; public int LiczbaPobranychPlikow { get {
return liczbaPobranychPlikow; } set { if (value ==
liczbaDoPobraniaPlikow) { if (SkonczonePobieranie != null)
SkonczonePobieranie(); } liczbaPobranychPlikow = value; } } private
int liczbaDoPobraniaPlikow; public int LiczbaDoPobraniaPlikow { get
{ return liczbaDoPobraniaPlikow; } } }
87. ZDARZENIA W WPF
88. Zdarzenia w WPF Pisaem ju wczeniej , e WPF, Silverlight,
ASP.NET w swoich klasach i kontrolkach uywa zdarzeo do kontrolki
nad graficznym interfejsem uytkownika. Uczc si ktrej z tych
technologii czasami spotkasz si ze zdarzeniami. Nawet pocztkujcy
programici z nich korzystaj i nie wiedz dokadnie jak one dziaaj
poniewa wymaga to poznania wielu zagadnieo jak np. delegaty. No c ,
dla uproszczenia nie bd w tym wpisie zagbiad si jak zdarzenia s
skonstruowane w ASP.NET. Zobaczmy jak zdarzenia s zrobione w WPF
zwaszcza , e WPF i Silverlight w tym wypadku powinni byd do siebie
podobni. Kontrolka przycisku dziedziczy po klasie bazowej
ButtonBase. Ma to sens poniewa w WPF s te inne przyciski od tego
standardowego jak np. ToggleButton.
89. public class Button : ButtonBase
90. Przycisk dziedziczy po niej zdarzenie Click , ktry jest
typem delegaty RoutedEventHandler. Delegata ta spodziewa si dwch
parametrw: referencji do obiektu, ktry spowodowa wywoanie tego
zdarzenia oraz obiekt klasy RoutedEventArgs , ktry przechowuje rne
dodatkowe informacje na temat tego zdarzenia. Jest to pomysowe
poniewa nie chciaby widzied caej linijki parametrw za kadym razem
gdy obsugujesz dane zdarzenie.
91. public abstract class ButtonBase : ContentControl,
ICommandSource { public event RoutedEventHandler Click; // Summary:
// Raises the System.Windows.Controls.Primitives.ButtonBase.Click
routed event. protected virtual void OnClick();
92. Button Klasa ButtonBase posiada te metod wirtualn dostpn
tylko dla klas pochodnych, ktra moe wywoad bezporednio to
zdarzenie. Klasa Button uruchamia to zdarzenie gdy klikniesz na
przycisk . Jednak co dokadnie si dzieje w momencie jego kliknicia?
Skd klasa to wie ? To wychodzi poza ramy tego wpisu. W WPF mamy
XAML , a w nim najczciej mwimy, ktra kontrolka obsuguje jakie
zdarzenie. Jest to wygodne ale warto sobie uwiadomid , e kod czcy
nasz metod np. Button_Click z wydarzeniem wci istnieje jest on
tylko wygenerowany przez kompilator. W sumie to duo rzeczy w
kompilatorze si dzieje aby powizad kod XAML z kodem w C#.
94. Button Zdarzenia w wielu kontrolkach dziaaj wedug tego
samego wzoru. Sygnatura delegata w zdarzeniach w kontrolkach jest
prawie zawsze taka sama. Delegata mwi , e ta metoda nic nie moe
zwracad void oraz pokazuje dwa parametry: sender: Referencja do
kontrolki, ktra wywoaa dane zdarzenie. e: Zbir pomocniczych
argumentw, ktre otrzymao dane zdarzenie. Majc do dyspozycji
argument seneder teraz nic nie stoi na przeszkodzie aby dana metoda
X obsugiwaa zdarzenie Click dla 100 przyciskw skoro moesz
sprawdzid, ktry z nich wywoa to zdarzenie.
95. Koniec Do zobaczenia Do nastpnego wykadu o LINQ