Python


Dedovanje

Jasno, razredi izgledajo kar v redu, vendar na videz ne nudijo kaj več kot že omenjeni slovarji. Obstaja pa nekaj pomembnega, kar to podobnost razbije. To je  dedovanje. Dedovanje deluje tako:

Recimo, da programiramo igrico. V igrici predvidimo, da se branimo pred napadalci. Napadalci se med igro premikajo, streljajo krogle in so lahko ustreljeni. Ob zadetku se zdravje napadalcu poslabša. Vsak napadalec ima 10 nabojev (krogel).  Napadalce predstavimo z razredom:

    class Napadalec:
tip = "kakrsenkoli"
def __init__(self, x, y):
self.zdravje = 100 # vsak zacne s 100% zdravjem
self.naboj = 10 # in 10 naboji
self.x_polozaj = x
self.y_polozaj = y
def premakni(self, dx, dy): # dx and dy pove "kako dalec se premakne"
self.x_polozaj = self.x_polozaj + dx
self.y_polozaj = self.y_polozaj + dy
def streljaj(self, smer):
self.naboj = self.naboj - 1
igra.dodajKroglo(self.x_polozaj, self.y_polozaj, smer)
# predpostavimo, da je "igra" objekt, tvorjen kje drugje
def siZadet(self):
self.zdravje = self.zdravje - 10 # au- boli!! - zdravje se poslabsa

Že kar vidimo, da bo to zanimiva igrica! Vendar nekaj manjka. Če uničujemo ves čas enake napadalce, bo stvar dolgočasna.Skušajmo uvesti več vrst sovražnikov.  Vsi sovražniki  bodo podobni napadalcem.  Vsak bo imel števec življenj, vsak bo imel svoj položaj, vsak bo lahko streljal. V določenih vidikih pa se bodo razlikovali. Zato bomo vsakega novega sovražnika izpeljali iz originalnega napadalca in pri tem uporabili takoimenovano dedovanje.  Dedovanje omogoča tvorbo novega razreda  tako, da se pri definiciji pomagamo z uporabo osnovnega razreda, vendar novemu razredu kaj dodamo.  Poglejmo primer:

    class Konjenik(Napadalec):		# ta napadalec bo torej hitrejsi
tip = "konjenik"
def premakni(self, dx, dy):
self.x_polozaj = self.x_polozaj + 3*dx # konjenik se premika hitro
self.y_polozaj = self.y_polozaj + 3*dy

class Topnicar(Napadalec): # ta napadalec bo topnicar, opremljen z granatami
type = "topnicar"
def __init__(self, x, y):
Napadalec.__init__(self, x, y) # inicializacija osnovnega razreda
self.granate = 10
def izstreliGranato(self, smer):
self.granate = self.granate - 1
igra.dodajGranato(self.x_polozaj, self.y_polozaj, smer)
def siZadet(self):
self.zdravje = self.zdravje - 5 # zadetek zascitenega topnicarja manj poskoduje

Definiciji razreda Konjenik sledita oklepaja, v katerih je podan osnovni razred, iz katerega je izpeljan novi razred (Konjenik). To pomeni, da bo Konjenik imel vse podatkovne elemente in metode, ki so opisane v razredu Napadalec, vseboval pa bi lahko še dodatne podatkove elemente in metode. V razredu Konjenik nismo dodali nič novega, pač pa smo nadomestili  metodo premik() z drugo metodo. Ta, druga metoda je podobna prejšnji, vendar se konjenik premika 3 krat hitreje od navadnega napadalca.  

Tank je prav tako izpeljan iz napadalca, vendar smo mu dodali rakete. Ker želimo, da bo vsak novi tank imel v začetku 10 raket, smo tvorili nov konstruktor (__init__), ki to naredi za nas. Ker smo nadomestili originalni konstruktor, ga moramo klicati eksplicitno, če naj bi se (originalni konstruktor) izvedel. Tanku smo dodali še metodo za izstreljevanje raket.

Končno se lahko lotimo pisanja igrice. Na primer tako:

    from whrandom import random
from Napadalci import *
from mojaIgra import Igra

sovrazniki = []
for i in range(100):
x = random(100)
y = random(100)
sovrazniki.append(Napadalec(x, y))
for i in range(20):
x = random(100)
y = random(100)
sovrazniki.append(Konjenik(x, y))
for i in range(10):
x = random(100)
y = random(100)
sovrazniki.append(Topnicar(x, y))

igra = Igra()
while not igra.konec():
for i in range(len(sovrazniki)):
sovrazniki[i].streljaj(random(360))
if sovrazniki[i].tip == "topnicar":
sovrazniki[i].izstreliGranato(random(360))
sovrazniki[1].premakni(random(10),random(10))
igra.nekajNaredi()
igra.izpisRezultatov()


Sedaj pa domača naloga:

Tvori razred Vozilo z  naslednjimi lastnostmi in metodami:

Tvori razred Letalo, izpeljan iz razreda Vozilo. Letalo naj ima naslednje dodatne lastnosti oziroma metode:

Tvori razre Avto, izpeljan iz razreda Vozilo.   Avto naj ima naslednjo dodatno metodo:

Vse skupaj shrani v datoteko vozila.py. Nato sestavi preskusni program, ki naj izgleda približno tako:

    from vozila import *

cessna = Letalo(100,10,"gor") # polozaj 100, hitrost 10, zakrilca gor
golf = Auto(100,-10) # polozaj 200, hitrost 80

print "letalo:", cessna.polozaj, cessna.zakrilca
print "Avto:", golf.polozaj, golf.hitrost

cessna.premik()
avto.premik()
cessna.spustiZakrilca()
golf.pritisniZavoro()

print "letalo:", cessna.polozaj, cessna.zakrilca
print "Avto:", golf.polozaj, golf.hitrost

Kam nas vse to pelje? Odgovor dobiš kasneje, ko spoznamo osnove programiranja grafičnega uporabniškega vmesnika (GUI, Graphical User Interface). Sedaj je že čas, da prej spoznamo, kako se reševati iz napak, ki se pri programiranju nedvomno dogajajo.