PDF

Polymorfizmus

Štrnásta prednáška

Formát
PDF
Veľkosť
3,9 MB
Pridané
Stiahnutí
792
Stiahnuť PDF · 3,9 MB

Preber si túto poznámku so svojou AI

Skopíruj pripravený podklad a vlož ho do ChatGPT, Claude alebo inej AI — bude ťa učiť alebo skúšať len z tejto poznámky.

Otvoriť AI: ChatGPT · Claude · Gemini

Náhľad poznámky

Polymorfizmus

Informatika 2

Pojmy zavedené v 2. prednáške(1)

• implementačná závislosť – minimálna
• súdržnosť – maximálna
• zodpovednosť – jedna jasne definovaná

– miery dobrého návrhu tried

• duplicita kódu – súdržnosť
• priamy prístup k atribútom – závislosť,

zodpovednosť

Informatika 2

1

Pojmy zavedené v 2. prednáške(2)

• refaktoring
• zmena kódu bez zmeny jeho funkcie
• úpravy pre zlepšenie miery závislosti, súdržnosti a

zodpovednosti

• overenie korektnosti refaktoringu – regresné

testovanie

Informatika 2

2

Pojmy zavedené v 2. prednáške(3)

• HashMap – kontejner
• neusporiadaná množina usporiadaných dvojíc

(kľúč, hodnota)

• kľúč – unikátny
• poskytuje hodnoty určené kľúčom
• prechádzanie kontejnerom – cyklus for each

Informatika 2

3

h

ttp://xk

cd.

com/888/

Ako sa úpravy programu tvária

Informatika 2

4

Aké sú v skutočnosti

Informatika 2

5

h

ttp://xk

cd.

com/724/

Cieľ prednášky

• polymorfizmus
• interface

• príklad: hra „World of FRI“

Informatika 2

6

„World of FRI“

• ľubovoľné smery
• bez implementačnej závislosti
• výsledok refaktoringu

Informatika 2

7

Nová úloha

• pridať nový príkaz „ukaz“
• do terminálového okna sa vypíše informácia o

miestnosti, v ktorej sa hráč nachádza

• kde sa pracuje s príkazmi?

Informatika 2

8

WoF

– diagram tried

Informatika 2

9

Kde sa pracuje s príkazmi?

Informatika 2

10

• trieda NazvyPrikazov

– udržiava zoznam názvov príkazov
– odpovedá na otázku „jePrikaz“

• trieda Parser

– načítava text príkazu z okna terminálu
– rozkladá ich na dvojice príkaz, parameter
– požiada o inštanciu triedu Prikaz

Kde sa pracuje s príkazmi?

• trieda Prikaz

– uchováva názov príkazu a prípadný parameter

• trieda Hra

– vykonáva príkazy

Informatika 2

11

Úlohy triedy Hra

1. Riadenie priebehu hry
2. Udržiavanie informácii o hráčovi (aktuálna

miestnosť)

3. Vytváranie miestností – „mapa hry“
4. Vykonávanie príkazov

• veľa úloh – refaktoring

Informatika 2

12

Refaktoring triedy Hra(1)

• informácie o hráčovi do samostatnej triedy
• vytvorenie mapy hry do samostatnej triedy

Informatika 2

13

Refaktoring triedy Hra(1)

Informatika 2

14

Trieda MapaHry

Informatika 2

15

Trieda Hrac

Informatika 2

16

Vykonávanie príkazov

• Hra – metóda vykonajPrikaz

• možnosti:

– trieda Prikaz
– nová trieda

• vykonávanie príkazu –> práca s dátami príkazu –>

zodpovednosť triedy Prikaz

Informatika 2

17

Metóda vykonajPrikaz v triede Hra(1)

private boolean vykonajPrikaz(Prikaz paPrikaz)
{
boolean jeKoniec = false;
if (paPrikaz.jeNeznamy()) {
System.out.println("Nerozumiem");
return false;
}
...

Informatika 2

18

Metóda vykonajPrikaz v triede Hra(2)

...
String nazovPrikazu = paPrikaz.dajNazov();
if (nazovPrikazu.equals("pomoc")) {
vypisNapovedu();
} else if (nazovPrikazu.equals("chod")) {
chodDoMiestnosti(paPrikaz);
} else if (nazovPrikazu.equals("ukonci")) {
jeKoniec = ukonciHru(paPrikaz);
}
return jeKoniec;
}

Informatika 2

19

Závyslosti metódy vykonajPrikaz

• metóda vykonajPrikaz v hre je závislá od metód:

– vypisNapovedu
– chodDoMiestnosti
– ukonciHru

• tieto metódy treba preniesť tiež

Informatika 2

20

Sprístupnenie hráča v triede Prikaz

• v hre je hráč atributom aHrac
• v príkaze ako parameter metódy vykonaj

• v hre je príkaz parametrom metódy vykonajPrikaz
• v príkaze sú vlastnosti príkazu priamo prístupné

Informatika 2

21

Metóda vykonaj v triede Prikaz(1)

public boolean vykonaj (Hrac paHrac)
{
boolean jeKoniec = false;
if(jeNeznamy()) {
System.out.println("Nerozumiem");
return false;
}
...

Informatika 2

22

Metóda vykonaj v triede Prikaz(2)

...
String nazovPrikazu = dajNazov();
if (nazovPrikazu.equals("pomoc")) {
vypisNapovedu();
} else if (nazovPrikazu.equals("chod")) {
chodDoMiestnosti(paHrac);
} else if (nazovPrikazu.equals("ukonci")) {
jeKoniec = ukonciHru();
}
return jeKoniec;
}

Informatika 2

23

Kde sa pracuje s príkazmi?

• trieda Prikaz

– uchováva názov príkazu a prípadný parameter
– vykonáva príkazy

• trieda Hra

– žiada príkaz o vykonanie (ako celok)

Informatika 2

24

Úlohy triedy Hra

1. Riadenie priebehu hry

• refaktoring dokončený
• rozšírenie funkcií hry – príkaz ukaz

Informatika 2

25

Nový príkaz „ukaz“

• dve rôzne riešenia

– nový príkaz do triedy Prikaz
– nové triedy – vykonanie každého príkazu

Informatika 2

26

Nový príkaz do triedy Prikaz

• pozitívum riešenia

– mechanické rozšírenie súčasného stavu

• negatíva riešenia

– zväčší sa veľkosť triedy
– zhoršuje sa udržiavateľnosť

Informatika 2

27

Triedy na vykonávanie

• riešenie – vykonávanie každého príkazu (podľa

názvu) v samostatnej triede

• pozitívum riešenia

– každá trieda má jasne určenú zodpovednosť
– pridanie príkazov nemá vplyv na už zavedené

• negatívum riešenia

– väčší počet tried

Informatika 2

28

Refaktoring – triedy vykonavacov

• VykonavacChod

– void vykonaj(Hrac paHrac, String paParameter)

• VykonavacPomoc

– void vykonaj()

• VykonavacUkonci

– boolean vykonaj(String paParameter)

Informatika 2

29

Model tried „WoF“

Informatika 2

30

Ukážka novej triedy

public class VykonavacPomoc
{
public void vykonaj()
{
System.out.println("Zabludil si. Si sam. Tulas sa po fakulte.");
System.out.println();
System.out.println("Mozes pouzit tieto prikazy:");
System.out.println(" chod ukonci pomoc");
}
}

Informatika 2

31

32

Informatika 2

Metóda vykonaj v triede Prikaz

if (nazovPrikazu.equals("pomoc")) {
vypisNapovedu();
} else if (nazovPrikazu.equals("chod")) {
...

if (nazovPrikazu.equals("pomoc")) {
VykonavacPomoc vykonavac;
vykonavac = new VykonavacPomoc();
vykonavac.vykonaj();
} else if (nazovPrikazu.equals("chod")) {
...

Metóda vykonaj v triede Prikaz – cieľ

public boolean vykonajPrikaz(Hrac paHrac)
{
if (jeNeznamy()) {
System.out.println("Nerozumiem");
return false;
}

Vykonavac vykonavac;
vykonavac = aPrikazy.dajVykonavac(aNazov);
return vykonavac.vykonaj(paHrac, aParameter);
}

Informatika 2

33

Polymorfizmus(1)

• riešenie možné vďaka polymorfizmu

• polymorfizmus:

využitie určitej špeciálnej situácie, keď dva rôzne
objekty môžu prijať tú istú správu a pritom každý
z nich reaguje inak – použije inú metódu

Informatika 2

34

Polymorfizmus(1)

• odosielateľ správy sa nestará o typ adresáta

– zjednodušenie na strane odosielateľa

• postačuje, že adresát je schopný správu prijať

– má správu v rozhraní

• každý adresát použije svoju metódu

Informatika 2

35

Polymorfizmus - druhy





• preťažovanie – metódy a konštruktory s rôznym

typom alebo počtom parametrov

• pretypovávanie – autoboxing
• parametrický – generické triedy

Informatika 2

36

polymorfizmus

ad-hoc

univerzálny

preťažovanie

parametrický

pretypovanie

inkluzívny

Protokol: správa → metóda

• jedna správa

• rôzne metódy

Informatika 2

37

vykonavac.vykonaj()

{VykonavacPomoc.} vykonaj

{VykonavacChod.} vykonaj

{VykonavacUkonci.} vykonaj

odosielateľ

adresát

{alebo}

Prostriedky jazyka Java

• správa v rozhraní – podmienka pre jej poslanie

• interface

– explicitná definícia zoznamu správ v rozhraní
– definuje typ objektových premenných

• trieda implementuje interface

– zaručuje, že má implementované všetky metódy pre

správy uvedené v interface

– inštancie sú schopné chovať sa polymorfne - inkluzívny

Informatika 2

38

Aplikácia interface do hry

Informatika 2

39

Interface IVykonavac




• kľúčové slovo interface
• správy bez modifikátora prístupu ukončené ;
• vždy public

Informatika 2

40

public interface IVykonavac
{
boolean vykonaj(Hrac paHrac, String paParam);
}

Implementácia rozhrania

• explicitné uvedenie inteface v hlavičke triedy
• ľubovoľný počet implementovaných interface

• metódy pre všetky správy z interface

– musia byť verejné
– správy sa musia presne zhodovať

Informatika 2

41

Java – implementácia rozhrania

public class VykonavacPomoc implements IVykonavac
{
public boolean vykonaj(Hrac paHrac, String paParam)
{
System.out.println("Zabludil si. Si sam.");
System.out.println();
System.out.println("Mozes pouzit tieto prikazy:");
System.out.println(" chod ukonci pomoc");
return false;
}
}

Informatika 2

42

Interface v UML(1)

• obdĺžnik – ako trieda
• stereotyp «interface» nad menom
• len správy inštancii

Informatika 2

43

Interface v UML(2)

Informatika 2

44

Poslanie správy prem. typu interface

IVykonavac vykonavac;
vykonavac = aPrikazy.dajVykonavac(aNazov);
vykonavac.vykonaj(paHrac, aParameter);

Informatika 2

45

Statický kontra dynamický typ(1)

• statický typ

– uvedený v definícii objektovej premennej
– určuje sa pri preklade
– určuje množinu správ, ktoré je možno poslať (iné nie)

• dynamický typ

– skutočný typ objektu referencovaného premennou
– určuje sa za behu pri priradení hodnoty premennej
– určuje chovanie objektu, reakcie na správy

Informatika 2

46

47

Informatika 2

Statický kontra dynamický typ(2)

IVykonavac vykonavac;
vykonavac = aPrikazy.dajVykonavac(aNazov);
vykonavac.vykonaj(paHrac, aParameter);

statický typ

dynamický typ
nevieme odvodiť z príkazu
môže byť
VykonavacUkonci, VykonavacPomoc, VykonavacChod

48

Informatika 2

Spracovanie správy pri polymorfizme(1)

vykonavac.vykonaj(paHrac, aParameter);

VykonavacPomoc

49

Informatika 2

Spracovanie správy pri polymorfizme(1)

vykonavac.vykonaj(paHrac, aParameter);

VykonavacUkonci

Statický kontra dynamický typ

• príkaz bol rovnaký
• statický typ je rovnaký

• vykonávajú sa rôzne metódy

Informatika 2

50

Metóda dajVykonavac v NazvyPrikazov

public IVykonavac dajVykonavac(String paNazov)
{
if (paNazov.equals("pomoc")) {
return new VykonavacPomoc();
} else if (paNazov.equals("chod")) {
return new VykonavacChod();
} else if (paNazov.equals("ukonci")) {
return new VykonavacUkonci();
}
return null;
}

Informatika 2

51

Typová kompatibilita a interface

• inštancia je typovo kompatibilná s interface ak jej

trieda implementuje daný interface

• hodnota null je typovo kompatibilná so všetkými

interface

Informatika 2

52

Typová kompatibilita v dajVykonavac(1)

public IVykonavac dajVykonavac(String paNazov)
{
if (paNazov.equals("pomoc")) {
return new VykonavacPomoc();
} else if (paNazov.equals("chod")) {
return new VykonavacChod();
} else if (paNazov.equals("ukonci")) {
return new VykonavacUkonci();
}
return null;
}

Informatika 2

53

class VykonavacUkonci implements IVykonavac

Typová kompatibilita v dajVykonavac(2)

public IVykonavac dajVykonavac(String paNazov)
{
if (paNazov.equals("pomoc")) {
return new VykonavacPomoc();
} else if (paNazov.equals("chod")) {
return new VykonavacChod();
} else if (paNazov.equals("ukonci")) {
return new VykonavacUkonci();
}
return null;
}

Informatika 2

54

Zjednodušenie pomocou HashMap

• inštancie vykonávačov nemajú atribúty
• => nemenia svoj stav
• => všetky inštancie budú mať rovnaký stav
• => možno ich predpripraviť do zoznamu

Informatika 2

55

Trieda NazvyPrikazov s HashMap(1)

private final HashMap<String, IVykonavac> aVykonavace;

public NazvyPrikazov()
{
aVykonavace = new HashMap<String, IVykonavac>();

aVykonavace.put("pomoc", new VykonavacPomoc());
aVykonavace.put("chod", new VykonavacChod());
aVykonavace.put("ukonci", new VykonavacUkonci());
}

Informatika 2

56

Trieda NazvyPrikazov s HashMap(1)

public boolean jePrikaz(String paNazov)
{
return aVykonavace.containsKey(paNazov);
}

public IVykonavac dajVykonavac(String paNazov)
{
return aVykonavace.get(paNazov);
}

Informatika 2

57

Nový príkaz ukaz

• refaktoring
• jednoduché pridávanie príkazov

1. nová trieda – vykonávač
2. zaradenie inštancie do HashMap

Informatika 2

58

Pridanie nového príkazu – vykonávač

public class VykonavacUkaz implements IVykonavac
{
public boolean vykonaj(Hrac paHrac, String paPar)
{
Miestnost akt = paHrac.dajAktualnuMiestnost();
System.out.println(akt.dajUplnyPopis());

return false;
}
}

Informatika 2

59

Pridanie nového príkazu – HashMap

aVykonavace = new HashMap<String, IVykonavac>();

aVykonavace.put("pomoc", new VykonavacPomoc());
aVykonavace.put("chod", new VykonavacChod());
aVykonavace.put("ukonci", new VykonavacUkonci());
aVykonavace.put("ukaz", new VykonavacUkaz());

Informatika 2

60

Konečný stav

Informatika 2

61

Vďaka za pozornosť

Automaticky vygenerovaný textový náhľad. Pre plné formátovanie si stiahnite súbor.