Temat: Klasy zagnie d one. Dziedziczenie. Dziedziczenie a

Transkrypt

Temat: Klasy zagnie d one. Dziedziczenie. Dziedziczenie a
Temat: Klasy zagnie d one. Dziedziczenie. Dziedziczenie a
hermetyzacja. Polimorfizm i metody wirtualne.
1. Klasy zagnie d one
Przykład 1
Klasy zagnie d one
class Bank
{
public class Konto
{
private double stan;
public void UstawStan(double s) { stan = s; }
private void f()
{
Kredyt K = new Kredyt();
K.UstawDlug(1000.0);
K.dlug = 500.0; // bład !!!
}
} // koniec deklaracji klasy Konto
private class Kredyt
{
private double dlug;
public void UstawDlug(double d) { dlug = d; }
private void g()
{
Konto K = new Konto();
K.UstawStan(1500.0);
K.stan = 1000.0; // bł d !!!
}
} // koniec deklaracji klasy Kredyt
private void h()
{
Konto Ko=new Konto();
Kredyt Kr=new Kredyt();
}
} // koniec deklaracji klasy Bank
class Program
{
static void Main( )
{
Bank.Konto Ko=new Bank.Konto();
Bank.Kredyt Kr=new Bank.Kredyt(); // bł d !!!
}
}
• Klasy Kredyt i Konto s dost pne w klasie Bank.
• Klasa Kredyt jest dost pna w klasie Konto i odwrotnie.
• Klasa Kredyt jest prywatna w klasie Bank i nie jest dost pna na zewn trz
klasy Bank
• Prawa dost pu do klasy zewn trznej nie s zatem takie same jak dla klasy
wewn trznej. Klasa zewn trzna nie mo e by zadeklarowana jako
prywatna.
• Klasy zagnie d one mog by zadeklarowane jako publiczne albo
prywatne.
Przykład 2
Klasy zagnie d one
class Bank
{
class Konto { ... } // klasa Konto jest prywatna
public Konto OtworzPubliczneKonto( ) // bł d !!!
{
Konto O = new Konto( );
O.Ustaw( );
return O;
}
private Konto OtworzPrywatneKonto( )
{
Konto O = new Konto( );
O.Ustaw( );
return O;
}
}
• Klasa Konto jest dost pna w metodach OtworzPubliczneKonto i
OtworzPrywatneKonto, poniewa obydwie metody nale do klasy Bank.
Jednak metoda OtworzPubliczneKonto nie skompiluje si , poniewa jest
to metoda publiczna, a powinna by prywatna, skoro działa na prywatnej
klasie Konto.
2. Dziedziczenie
• Klasa potomna dziedziczy z klasy bazowej:
- wszystkie dane składowe,
- wszystkie metody oprócz konstruktorów i destruktorów.
• Nie mo na dziedziczy z prywatnej wewn trznej klasy.
Przykład 3
Prosta hierarchia klas
class Pojazd{
double maks_predkosc;
public void Ruch( )
{
…………
}
}
class Samochod:Pojazd{
double moc_silnika;
public void Jedz()
{
............
}
}
Samochod S=new Samochod();
Pojazd
Samochód
Przykład 4
Prosta hierarchia klas
class Przyklad
{
private class WewnetrznaBazowa{ }
public class WewnetrznaPotomna:WewnetrznaBazowa{ }
// bład !!!
}
Dost p do elementów klasy bazowej
• Elementy klasy potomnej maj dost p do elementów typu protected i
public z klasy bazowej.
• Publiczne składniki klasy bazowej s
potomnej.
publiczne równie
w klasie
• Prywatne składniki klasy bazowej s niedost pne w klasie potomnej.
• Elementy typu protected s dost pne wył cznie w klasie, w której s
definiowane oraz we wszystkich klasach potomnych tej klasy.
• Elementy typu proteced nie s dost pne w klasach, które nie s potomne
w stosunku do klasy, w której te elementy s definiowane.
• Elementy typu protected w danej klasie bazowej s
protected w klasie potomnej.
Przykład 5
Dost p do elementów klasy bazowej
class Bazowa{
protected string name;
public int a;
int b;
}
class Potomna: Bazowa{
public void f()
{
Console.WriteLine(name);
a++ ;
b++; // bł d !!!
}
}
class PotomnaPotomnej: Potomna
{
protected void g( )
{
Console.WriteLine(name);
a++ ;
b++; // bł d !!!
}
}
class Program{
static void Main()
{
PotomnaPotomnej D=new PotomnaPotomnej();
D.a=2;
D.b=3; // bł d !!!
równie
typu
D.name="Test"; // bł d !!!
D.f();
D.g();// bł d !!!
}
}
• Je eli klasa bazowa nie ma jawnego konstruktora, a klasa potomna ma
jawny konstruktor, to na rzecz instancji klasy potomnej najpierw wywoła
si konstruktor domy lny klasy bazowej, a potem konstruktor klasy
potomnej.
• Je eli klasy: bazowa i potomna nie maja jawnego konstruktora, to
kompilator wygeneruje konstruktory domy lne dla tych klas i przy
tworzeniu instancji klasy potomnej najpierw wywoła konstruktor
domy lny klasy bazowej a potem konstruktor domy lny klasy potomnej.
• Je eli klasa bazowa ma tylko jawny konstruktor, który nie jest domy lny,
to w konstruktorze klasy potomnej nale y wywoła konstruktor klasy
bazowej, stosuj c słowo base.
Przykład 6
Wywołanie konstruktorów klasy bazowej
class Token{
protected Token(string name) { ... }
}
class CommentToken : Token{
public CommentToken(string name) { ... } // bł d !!!
}
//-----------------------------------------------------class Token{
protected Token() { }
public Token(string name) { }
}
class CommentToken : Token{
public CommentToken(string name) { }
}
//-----------------------------------------------------class Token{
public Token(string name) { }
}
class CommentToken : Token{
public CommentToken(string name) : base(name) { }
}
Przykład 7
Wywołanie konstruktorów klasy bazowej
class Bazowa{
private Bazowa() { ... }
}
class Potomna : Bazowa{
public Potomna() { ... } // bł d !!!
}
• Mo na u y słowa base tak e, aby zaznaczy odniesienie do tych samych
identyfikatorów, które zostały zadeklarowane w klasie bazowej i
potomnej.
Przykład 8
Odwołanie do składników klasy bazowej o tej samej nazwie co w klasie
potomnej
class Token{
protected string name;
protected void f() {……}
}
class CommentToken: Token{
public void Method(string name)
{
base.name = name;
base.f();
}
}
3.
Metody wirtualne
• Metoda wirtualna to metoda, która mo e by nadpisana (przedefiniowana)
w klasie potomnej i wywołana polimorficznie, tj. inaczej na rzecz
instancji klasy bazowej i inaczej na rzecz instancji klasy potomnej.
• Aby zadeklarowa metod
nagłówku tej metody.
wirtualn
trzeba wpisa
słowo virtual w
• Aby nadpisa metod wirtualn w klasie potomnej nale y wpisa słowo
override w deklaracji metody przedefiniowuj cej.
Przykład 9
Metoda wirtualna i jej polimorficzne wywołanie
class Instrument
{
public virtual void Play()
{
Console.WriteLine("Jakis instrument gra ...");
}
}
class Piano : Instrument
{
public override void Play()
{
Console.WriteLine("Plim Plim Plim ....");
}
}
class Gitar : Instrument
{
public override void Play()
{
Console.WriteLine("Tran Tran Tran ....");
}
}
class Program
{
static void Concert(Instrument[] T)
{
for (int i=0;i<T.Length;i++)
T[i].Play();
}
static void Main()
{
Piano P = new Piano();
Gitar G = new Gitar();
Instrument[] T = new Instrument[2];
T[0] = P;
T[1] = G;
Concert(T);//polimorficzne wywołanie metody Play
}
}
Wynik:
Plim Plim Plim ....
Tran Tran Tran ....
• Metoda wirtualna nie mo e by zadeklarowana jako statyczna ani
prywatna.
Przykład 10
Przedefiniowywanie metod
class Token
{
protected virtual string Name() { ... }
}
class CommentToken : Token
{
public override void Name(int i) { ... } // bł d !!!
}
Przykład 11
Przedefiniowywanie metod
class Token
{
public virtual string Name() { ... }
}
class CommentToken : Token
{
public override string Name() { ... }
}
class OneLineCommentToken : CommentToken
{
public override string Name() { ... }
}
Przykład 12
Przedefiniowywanie metod
class Token
{
public virtual string Name() { ... }
}
class CommentToken : Token
{
public virtual override string Name() { ... }//bł d !!!
}
• Tylko metody wirtualne mog mie swoje przedefiniowane odpowiedniki
w klasach potomnych (metody typu override).
• Metody zarówno wirtualne jak i niewirtualne mog by ukryte, czyli
mog by zdefiniowane na nowo w klasach potomnych jako metody typu
new.
• Metoda mo e by jednocze nie wirtualna i typu new. Metoda taka
zast puje swój odpowiednik z klasy bazowej i mo e by polimorficznie
przedefiniowana w klasie potomnej.
• Je eli chcemy ukry metod wirtualn z klasy bazowej, czyli nie chcemy
tworzy przedefiniowania metody wirtualnej, tylko zdefiniowa zupełnie
now metod , to musimy wpisa new w nagłówku tej metody.
Przykład 13
Ukrywanie metod klasy bazowej
class Token
{
public virtual int LineNumber() { ... }
}
class CommentToken : Token
{
public int LineNumber() { ... } // Ostrze enie!!!
}
• Słowo new jest potrzebne tylko wtedy, gdy chcemy ukry metod o
identycznej sygnaturze z klasy bazowej.
Przykład 14
Ukrywanie metod klasy bazowej
class Token
{
public int LineNumber(short s) { ... }
}
class CommentToken : Token
{
new public int LineNumber(int i) { ... }//Ostrze enie!!!
}
Przykład 15
Ukrywanie metod klasy bazowej
class A
{
public virtual void M() { Console.Write("A"); }
}
class B : A
{
public override void M() { Console.Write("B"); }
}
class C : B
{
new public virtual void M() { Console.Write("C"); }
}
class D : C
{
public override void M() { Console.Write("D"); }
static void Main()
{
D d = new D(); C c = d; B b = c; A a = b;
d.M(); c.M(); b.M(); a.M();
}
}
Co sie uka e na ekranie w wyniku wykonania powy szego programu?
Odpowied : DDBB
Przykład 18
Przedefiniowywanie metod
class Base
{
public void Alpha( ) { ... }
public virtual void Beta( ) { ... }
public virtual void Gamma(int i) { ... }
public virtual void Delta( ) { ... }
private virtual void Epsilon( ) { ... } // bł d !!!
}
class Derived: Base
{
public override void Alpha( ) { ... }// bł d !!!
protected override void Beta( ) { ... } // bł d !!!
public override void Gamma(double d){ ... }// bł d !!!
public override int Delta( ) { ... } // bł d !!!
}

Podobne dokumenty