C# Mala Skola OOP-a

  • Upload
    bozapub

  • View
    150

  • Download
    4

Embed Size (px)

DESCRIPTION

C# Mala Skola OOP-a

Citation preview

  • NASTAVA RAQUNARSTVA

    Stanka Matkovi, Mijodrag urixi

    MALA XKOLA OBJEKTNO ORIJENTISANOGPROGRAMIRAA U PROGRAMSKOM JEZIKU C#

    Prvi deo

    Klasa, atributi i metodi

    Osnovni pojam u objektno orijentisanom programirau je klasa. Klasapredstava uopxtee objekata koji imaju zajedniqke osobine i funkcionalno-sti. Osobine opisujemo atributima a funkcionalnosti metodima.

    Posmatrajmo nastavni proces u xkoli. Recimo da u uqionici 1 uqenik IVa,Pera, radi zadatak iz matematike po zahtevu profesora Laze, a u uqionici 2profesor Mika predaje svim uqenicima odeea IVb novu lekciju iz fizike.Sasvim je mogue da sutradan uloge profesora budu promeene, pa da profesorMika u IVa ispituje ili predaje novu lekciju iz fizike, a profesor Laza u IVbpredaje novu lekciju iz matematike.

    Ve u ovom uproxenom prikazu nastavnog procesa moemo uoqiti osnovneobjekte koji uqestvuju u emu (Pera, Mika, Laza, IVa, IVb, matematika, fizika,uqionica 1, . . . ). Lako se moe uoqiti da Mika i Laza koordiniraju nastavniproces tako xto upoznaju uqenike sa novim gradivom, vrxe proveru znaa uqe-nika, oceuju ga, itd. Oni imaju i zajedniqke osobine (ime, struqna sprema,predmet koji predaju, godine staa). Samim tim oni pripadaju jednoj od klasauqesnika u nastavnom procesu, klasi Profesor. Na sliqan naqin moemo uoqitii klase Ucenik (Pera), Predmet (matematika, fizika), Odeljenje (IVa, IVb), . . .

    Do klasa dolazimo polazei od pojedinaqnih objekata. Posmatraem svihuqenika uoqavamo ihove zajedniqke osobine. Na primer, za sve uqenike je potre-bno pratiti ime, prezime, datum roea, razred, odeee. Te osobine nazivamoatributima. Takoe, svim uqenicima moemo pridruiti iste ,,akcije: uqe-nik odgovara i dobija ocenu, uqenik mea odeee . . . Te akcije u okviru klasenazivamo metodima klase, i ima se opisuje funkcionalnost objekata te klase.

    Klasu definixemo navoeem rezervisane reqi class iza koje sledi iden-tifikator klase (ime klase). Posle imena, ako formiramo klasu koja nasleujeneku, prethodno definisanu klasu, u zaglavu navodimo : pa ime klase iz ko-je je izvedena. Zatim navodimo telo klase u kome u vitiqastim zagradama {}definixemo qlanove klase (atributi i metodi).

  • Mala xkola objektno orijentisanog programiraa 27

    class :

    {opis / definicija clanova klase

    }

    Na primer, klasu uqenika moemo intuitivno definisati na sledei naqin:

    class Ucenik

    {string ime, prezime;

    DateTime datumRodjenja;

    int razred;

    int SkolskaGodina;

    char odeljenje;

    Ocena [] ocene;

    double prosek()

    {. . .

    }double prosek(Predmet P)

    {. . .

    }void uci(Lekcija X)

    {. . .

    }}

    Da bismo napravili objekat, upotrebavamo izraz oblika

    =new () .

    Korixeem operatora new odvaja se u dinamiqkoj memoriji prostor zaregistrovae objekta klase . Ovaj operator vraa adresu dodeenogprostora koju moemo dodeliti imenu objekta:

    Ucenik x=new Ucenik();

    Atributima opisujemo odreenu osobinu objekta (ime, prezime, datum roe-a, razred, odeee). Najqexe, razliqiti objekti iste klase imaju razliqitevrednosti atributa. Vrednosti atributa definixu stae objekta. Pri opisuatributa moramo navesti tip kome taj atribut pripada (celobrojni, realni, zna-kovni, . . . ) i ime atributa. Pristup atributima objekta neke klase realizujemona sledei naqin:

    imeObjekta.imeAtributa

  • 28 S. Matkovi, M. urixi

    Na primer, ako je x objekat klase Ucenik, atributu ime pristupamo na-voeem x.ime.

    Metodom opisujemo ponaxae objekta u odreenoj situaciji i pod odreenimuslovima (uci), ali i odreujemo nove vrednosti na osnovu osobina koje objekatposeduje (prosek). Na taj naqin opisujemo funkcionalnost objekta.

    Metod klase je imenovani blok naredbi koji se sastoji iz zaglava i telametoda. U zaglavu navodimo povratni tip (ako metod ne proizvodi vrednost kojuvraa, navodimo rezervisanu req void), zatim ime metoda za kojim sledi u malimzagradama spisak parametara metoda. Za svaki parametar navodi se tip kome tajparametar pripada kao i ime parametra. Posle zaglava u vitiqastim zagradamanavodimo telo metoda koje se sastoji iz odgovarajuih iskaza programskog jezikaC#.

    ()

    { }

    Poziv metoda objekta u programskom jeziku C# realizujemo na sledei na-qin:

    imeObjekta.imeMetoda(lista stvarnih parametara)

    Na primer, ako je x objekat klase Ucenik, metod prosek pozivamo sax.prosek(), a metod uci, x.uci(L) gde je L objekat klase Lekcija.

    Ukoliko u telu metoda koristimo neki od atributa ili pozivamo neki drugimetod te klase, ne navodimo ime objekta ve samo ime atributa, odnosno meto-de. Umesto imena objekta moemo navesti slubenu req this. Objekat kome seobraamo preko this je tekui objekat.

    Razliqiti metodi u jednoj klasi mogu imati isti naziv ali se moraju raz-likovati po broju ili tipu parametara. Pisae metoda istog imena a razliqi-tih parametara naziva se preklapae (overloading), preoptereivae metoda.U klasi Ucenik metod prosek smo preopteretili: za uqenika moemo raqunatiprosek svih zakuqenih ocena (prosek()), a moemo i prosek svih egovih ocenaiz datog predmeta (prosek(Predmet P)).

    Svojstva

    Jedna od najznaqajnih karakteristika objektno orijentisanog programiraaje enkapsulacija (zatvorenost, uqauree) objekata. Pod enkapsulacijom objek-ta podrazumevamo kontrolisan pristup elementima objekta. Nekim elementimaobjekta mogu pristupiti svi koji taj objekat na bilo koji naqin koriste. Te ele-mente nazivamo javnim (public) i oni qine deo preko koga objekat komunicirasa drugim objektima. Nasuprot ima postoji deo objekta koji ne koristimo di-rektno u komunikaciji sa drugim objektima, da ne bi bio izloen neovlaxenompristupu ili promeni. Za takve elemente kaemo da su privatni (private).

    Vrlo qesto postoji potreba da se atributi zaxtite od neovlaxenog pri-stupa ili promene pa su oni uglavnom privatni qlanovi klase, dok su metode uveini sluqajeva javne.

  • Mala xkola objektno orijentisanog programiraa 29

    Posmatrajmo klasu Vreme kojom emo opisivati trajae odreenih proce-sa. Vreme moemo definisati uz pomo razliqitih atributa na primer satima,minutama i sekundama, ili danima, satima, minutama i sekundama i sliqno. Dabismo xto efektnije prikazali razliqite elemente klase, vreme emo u primerukoji sledi definisati samo jednim atributom koji predstava broj sekundi.

    public class Vreme

    {long sekunde; // ili Int64 sekunde;

    public long VratiSate() // broj sati sadrzanih u vremenu

    {return sekunde / 3600;

    }public long VratiMinute() // broj minuta sadrzanih u vremenu

    {return sekunde/60;

    }public long VratiSekunde()

    {return sekunde ;

    }}

    Metodi VratiSate() i VratiMinute() raqunaju odreene informacije pa jerazlog ihovog postojaa intuitivno jasan. Postava se pitae zaxto postojimetoda VratiSekunde() kada broj sekundi sadranih u vremenu opisuje atributsekunde. Atribut sekunde je privatni qlan klase pa ne moemo saznati egovuvrednost van e. Zato uvodimo javni metod VratiSekunde() koji e nam omo-guiti pristup toj informaciji. Ovim metodom dobijamo informaciju o brojusekundi ali je i dae ne moemo promeniti (read-only).

    Radi lakxeg pristupa privatnim atributima klase u programskom jezikuC# moemo kreirati svojstva (property) i ona po potrebi mogu imati sledeekomponente: get, koja na osnovu vrednosti atributa odreuje i vraa neku karakteri-stiku objekta (korixeem naredbe return)

    set, koja na osnovu zadate vrednosti (value) raquna i postava vrednostiatributa.Svojstvo definixemo na sledei naqin:

    public

    {get { }set { }

    }

    Svojstva nisu ni atributi ni metode iako imaju karakteristike i atributai metoda. Kao i atributi svojstva nemaju parametre, a u ihovim komponentama,

  • 30 S. Matkovi, M. urixi

    kao i u metodama, moe se navesti proizvoan niz naredbi programskog jezikaC#. U get komponenti obavezno je navoee naredbe return kojom se vraaizraqunata vrednost.

    Svojstva se pozivaju navoeem imena objekta za kojim sledi ime svojstvaodvojeno taqkom. Ako se u izrazu poziv svojstva nalazi sa leve strane operatoradodele, izvrxava se set komponenta svojstva, a u suprotnom izvrxava se getkomponenta.

    U klasi Vreme moemo definisati svojstvo Sekunde na sledei naqin:

    public long Sekunde

    {get { return sekunde; }set { sekunde = value; }

    }

    Komponenta get ovog svojstva ima ekvivalentno dejstvo kao i metoda Vrati-Sekunde(), a set komponenta nam omoguava da postavamo vrednosti privatnomatributu sekunde. Ovako definisanim svojstvom naruxavamo enkapsulaciju jerje atribut sekunde postao potpuno dostupan. Samim tim mogli smo definisatiatribut kao javan. U veini sluqajeva potrebno je da van klase moemo proqi-tati vrednost atributa a da ga ne moemo meati. Tada koristimo svojstvo kodkojeg nije definisana set komponenta (read only svojstvo, samo za qitae).

    public long Sekunde

    {get { return sekunde; }

    }

    Ukoliko je vrednost atributa ograniqenog opsega, u set komponenti moemoizvrxiti kontrolu vrednosti koju postavamo. Na primer, ako klasu Vreme opi-sujemo atributima sat, minut i sekund, moemo proveravati da li je vrednostkoju postavamo za atribute minut i sekund u dozvoenim granicama (od 0 do59).

    Vrlo qesto postoje karakteristike objekta koje zavise i mogu se izraqunatina osnovu vrednosti atributa. Moemo definisati svojstva kojima odreujemovrednost tih karakteristika.

    Primetimo da objekte klase Vreme moemo opisati i pomou tri cela brojakoji predstavaju broj sati, minuta (minut

  • Mala xkola objektno orijentisanog programiraa 31

    {get { return (sekunde / 60) % 60; }

    }public long Sat

    {get { return sekunde / 3600; }

    }

    Ova svojstva nam omoguavaju da proqitamo vrednosti Sat, Minut i Sekund.Bilo bi prirodno da moemo i postaviti ihovu vrednost. Promena vrednostisvake od ovih karakteristika povlaqi i promenu atributa sekunde, pa moemorealizovati i odgovarajue set komponente.

    public long Sekund

    {get { return sekunde%60; }set { sekunde = sekunde-Sekund+value; }

    }public long Minut

    {get { return (sekunde / 60) % 60; }set { sekunde = sekunde-Minut*60+value*60; }

    }public long Sat

    {get { return sekunde / 3600; }set { sekunde = sekunde - Sat * 3600 + value * 3600; ; }

    }

    Indekseri

    U programskom jeziku C# moemo imati qlanove klase koje zovemo indekse-rima, koji imaju sliqnosti sa svojstvima ali i svojih specifiqnosti.

    Indekser nam omoguava da pojedinim karakteristikama objekata klase pri-stupamo na efikasan naqin, navoeem imena objekta i u uglastim zagradamaindeksa koji nas upuuje na odgovarajuu karakteristiku. Kao i svojstva, in-dekseri imaju get i set komponentu u kojima se u zavisnosti od vrednosti in-deksa odreuje karakteristika objekta, odnosno postavaju vrednosti atributa.Za razliku od svojstava indekser ima najmae jedan parametar a moe imati ivixe parametara, pa objekat dobija vixe dimenzija. Indekser definixemo nasledei naqin:

    public this[ , ...]

    {get { }set { }

    }

  • 32 S. Matkovi, M. urixi

    Indekseru programer ne zadaje ime jer on uvek koristi ime this. Sliqnometodama, indekseri mogu imati preklopene verzije, koje se moraju razlikovatipo broju ili po tipu indeksa.

    Klasu Vreme moemo proxiriti indekserom koji, u zavisnosti od indeksa,vraa Sat, Minut ili Sekund. Za indeks moemo izabrati: prethodno defini-sani nabrojivi tip (enum) qije su mogue vrednosti sat, minut i sekund, ilitip char tako da za vrednosti indeksa redom h, m i s vraa Sat, Minut iSekund, ili tip string. U navedenoj realizaciji indeksera koristimo pretho-dno definisana svojstva. Ovaj indekser mogli smo realizovati i bez korixeatih svojstava i u tom sluqaju on bi mogao i zameniti ta svojstva. Na sliqannaqin kako je realizovana set komponenta svojstava Sat, Minut i Sekund moemorealizovati set komponentu za svaki od navedenih indeksera.

    public enum JedinicaVremena

    {sat,

    minut,

    sekund

    };public long this[JedinicaVremena j]

    {get

    {if (j == JedinicaVremena.sat)

    return Sat; // return sekunde / 3600;

    if (j == JedinicaVremena.minut)

    return Minut; // return (sekunde / 60) % 60

    return Sekund;

    }}

    public long this[char ch]

    {get

    {if (ch == h)

    return Sat;

    if (ch == m)

    return Minut;

    if (ch == s)

    return Sekund;

    return sekunde;

    }}

    Ako je A objekat klase Vreme vrednost izraza A[JedinicaVremena.sat] iA[h] je broj sati sadranih u vremenu A.

  • Mala xkola objektno orijentisanog programiraa 33

    Konstruktori

    U C#-u pri deklaraciji neke instance klase, objekta, rezervixe se prostorza adresu objekta (referencu) a sam objekat se kreira korixeem operatoranew.

    = new () ;

    Operator new vraa adresu novog objekta koja se dodeuje imenu objekta.Konstruktor je metod koji se poziva pri kreirau objekta. Konstruktori su

    sastavni deo svake klase i nose eno ime. Pozivom konstruktora objekat poqiesvoj ivot. Klasa moe imati vixe konstruktora koji se razlikuju po listi pa-rametara. Lista parametara najqexe sadri vrednosti kojima inicijalizujemoatribute objekta, a moe biti i prazna.

    Ako pogramer ne napixe ni jedan konstruktor programski prevodilac enapraviti podrazumevani konstruktor (konstruktor bez parametara, numeriqkimtipovima dodeuje 0, logiqkim atributima dodeuje vrednost false, referentneatribute postava na null).

    Ako pixemo vixe konstruktora, kako svi imaju ime klase, moraju se razli-kovati po listi parametara, tj. po broju ili tipu parametara.

    Za klasu Vreme, definisanu u prethodnom delu qlanka, moemo definisatisledee konstruktore: Konstruktor bez parametara koji postava atribut sekunde na 0

    public Vreme()

    {sekunde = 0;

    } Konstruktor koji za parametar ima inicijalni broj sekundi

    public Vreme(long x)

    {sekunde = x;

    } Konstruktor koji za parametar ima broj sati i broj minuta

    public Vreme(long h, long m)

    {sekunde = 3600*h+60*m;

    } Konstruktor koji za parametar ima broj sati, minuta i sekundi

    public Vreme(long h, long m, long s)

    {sekunde = 3600 * h + 60 * m + s;

    } Konstruktor koji za parametar ima string oblika sati:minuti:sekunde(ukoliko se ovom konstruktoru prosledi drugaqiji format stringa on atri-but sekunde postava na 0)

  • 34 S. Matkovi, M. urixi

    public Vreme(string s)

    {try

    {long h = Convert.ToInt64(s.Substring(0, s.IndexOf(:)));

    long m = Convert.ToInt64(s.Substring(s.IndexOf(:) + 1,

    s.LastIndexOf(:) - s.IndexOf(:) - 1));

    long sek = Convert.ToInt64(s.Substring(s.LastIndexOf(:)+1));

    sekunde = 3600 * h + 60 * m + sek;

    }catch

    {sekunde = 0;

    }}

    Takozvani konstruktor kopije koji za parametar ima drugi objekat klaseVreme, v, sekunde postava na vrednost istog atributa parametra v.public Vreme(Vreme v)

    {sekunde = v.sekunde;

    }

    Zakuqak

    Ovo je prvi u nizu qlanaka koji planiramo, kojima emo pokuxati da pro-fesorima informatike pribliimo objektno orijentisano programirae i jedansavremeni programski jezik koji se, po naxim dosadaxim iskustvima, vrlo us-pexno moe upotrebiti u nastavi, u svim fazama uqea programiraa.

    U ovom qlanku smo vas upoznali sa osnovnim elementima klase a planiranoje da u naredna dva obradimo operatore i nasleivae.

    Predlaemo qitaocima da sliqno naxem primeru klase Vreme realizuju isledee klase:

    TackaDekart koja predstava taqku u Dekartovom koordinatnom sistemu zakoju moete definisati svojstva RastojanjeOdCentra, Kvadrant

    Krug, zadat sa dve dijametralno suprotne taqke, sa svojstvima Centar iPoluprecnik

    Vektor, zadat jednom taqkom u ravni, sa svojstvima Intezitet, FazniUgaoZa sve tri klase mogue je realizovati i raznovrsne konstruktore, kao i

    indeksere.

    Za kraj, evo i jednog segmenta koda pokazne aplikacije u kome se moe uo-qiti ispravan naqin pozivaa svakog od elemenata klase koju smo kroz qlanakobradili:

  • Mala xkola objektno orijentisanog programiraa 35

    //kreiranje objekta uz poziv podrazumevanog konstruktora

    Vreme T = new Vreme();

    //koriscenje set komponente svojstava Sat, Minut, Sekund

    T.Sat = 12;

    T.Minut = 70;

    T.Sekund = 0;

    //koriscenje get komponente indeksera sa enum indeksom

    Text=T[JedinicaVremena.sat]+" "+T[JedinicaVremena.minut];

    //kreiranje objekta uz poziv konstruktora sa parametrom tipa string

    T = new Vreme("12:46:30");

    //koriscenje get komponente svojstava Sat, Minut, Sekund

    label1.Text = T.Sat + " " + T.Minut + " " + T.Sekund;

    //kreiranje objekta uz poziv konstruktora sa parametrom tipa string

    T = new Vreme("1:20:4");

    //koriscenje get komponente indeksera sa char indeksom

    label1.Text += " " + T[h] + " " + T[m] + " " + T[s];

    Matematiqka gimnazija, Kraice Natalije 37, Beograd

  • NASTAVA RAQUNARSTVA

    Stanka Matkovi, Mijodrag urixi

    MALA XKOLA OBJEKTNO ORIJENTISANOGPROGRAMIRAA U PROGRAMSKOM JEZIKU C#

    Drugi deo

    Operatori

    Kao xto smo naglasili u prethodnom qlanku, metodom opisujemo ponaxaeobjekta u odreenoj situaciji i pod odreenim uslovima, odreujemo nove vre-dnosti na osnovu osobina koje objekat poseduje ali i opisujemo odreene akcijemeu objektima koje za rezultat imaju ili novi objekat ili neku vrednost.

    Lako se moe napraviti analogija izmeu ovakvih akcija i matematiqkihoperacija koje definixemo kao preslikavae skupa ureenih n-torki u neki skupobjekata ili vrednosti. U skladu sa tim u veini objektno orijentisanih pro-gramskih jezika postoji mogunost definisaa operatora, pre svega da bi se xtojednostavnije pozivali i xto efektnije koristili takvi metodi.

    U C# ne moemo definisati nove operatore ali u svakoj klasi moemopredefinisati veliki broj postojeih. Predefinisaem operatora u klasi do-deujemo operatoru novo znaqee koje se primeuje kada se operator poziva zaobjekte te klase. Ponaxae istog operatora za druge tipove objekata se ne mea.U tabeli koja sledi navedeni su operatori u C# koji se najqexe predefinixu.

    Unitarni operatori Binarni operatori

    +, , !, , ++, +, , , /, %, &, |, , ==, ! =, , =

    Predefinisaem operatora ne moemo promeniti arnost (broj operanada),prioritet i asocijativnost (grupisae) operatora.

    U opxtem sluqaju operator se zapisuje na sledei naqin:

    public static operator ()

    Slubena req static oznaqava da je operator statiqki qlan klase, xtoznaqi da nije kao ostali (,,ne statik) qlanovi vezan za objekat this ve za samuklasu. Kada je neki atribut klase static onda postoji samo jedna kopija tog

  • 32 S. Matkovi, M. urixi

    atributa koju dele svi objekti te klase. Kada je metod klase static on nije vezanza konkretni objekat klase, odnosno ne moe koristiti this. Statiqke metode sekoriste da izraqunaju odreene vrednosti a ne da promene stae objekta (Mathklasa u C# sadri statiqke metode Sqrt, Sin, Cos, . . . ). Statiqke qlanoveklase moemo koristiti bez kreiraa objekta.

    Operatori su static jer iako se primeuju na objektima klase nisu ihovsastavni deo niti ihova funkcionalnost ve su funkcionalnost klase. U nekim,starijim programskim jezicima operatori se vezuju za objekte ali je naqin nakoji su operatori realizovani u C# praktiqniji i prirodniji.

    Kod operatora moe biti bilo koji tip podataka definisanu C#, sistemski ili od strane korisnika. ime definixemo tip rezultataoperacije realizovane operatorom. Povratni tip ne moe biti void jer operatormora imati povratnu vrednost.

    Slubena req operator zajedno sa operacijskim znakom zapravo predstavaime metode. Skup moguih vrednosti za dat je prethodnonavedenom tabelom. Ukoliko izabrani operacijski znak predstava unarnu ope-raciju, sadri samo jedan parametar a ukoliko predstavabinarnu operaciju, sadri dva parametra meusobno odvo-jena zarezom. U svakoj bar jedan od parametara mora bitiobjekat klase qiji je operator qlan.

    U klasi Razlomak moemo definisati vixe operatora. Navodimo ispravnazaglava nekih od ih:

    public static Razlomak operator +(Razlomak a, Razlomak b)operator za odreivae zbira razlomaka a i b

    public static Razlomak operator *(Razlomak a, Razlomak b)operator za odreivae proizvoda razlomaka a i b

    public static Razlomak operator +(Razlomak a, int b)operator za odreivae zbira razlomka a i celog broja b

    public static Razlomak operator -(Razlomak a)operator za odreivae razlomka suprotnog znaka od razlomka a

    public static Razlomak operator ~(Razlomak a)operator za odreivae reciproqne vrednosti razlomka a

    public static Razlomak operator -(Razlomak a, Razlomak b)operator za odreivae razlike razlomaka a i b

    public static bool operator >(Razlomak a, Razlomak b)operator za proveru da li je razlomak a vei od razlomka b

    U telu operatora mora postojati jedna ili vixe komandi return gde je proizvoan izraz tipa .

  • Mala xkola objektno orijentisanog programiraa 33

    Unarni operatori se pozivaju prefiksno, . Operatori ++ i imaju i postfiksnu notaciju pa se mogu pozi-vati i postfiksno, . Binarni operatorise pozivaju infiksno .

    U sledeem segmentu komandi C# navodimo ispravne pozive operatora klaseRazlomak qija su zaglava prethodno navedena.

    Razlomak x = new Razlomak(3, 4);

    Razlomak y = new Razlomak(-12, 5);

    Razlomak z;

    z = x + y;

    z = x + 5;

    z = ~x;

    z = -y;

    if (x > y)

    z = x y*z + 3;

    else

    x += y;

    Predefinisaem binarnih operatora +,, , /,%,&, |, , automatskisu predefinisani i operator + =, =, =, / =,% =,& =, | =, =, =.

    Operatori za poreee moraju biti predefinisani u paru. Ako predefi-nixemo operator == onda moramo predefinisati i operator ! =. Sliqno i zaoperatore i =.

    Klasa Razlomak

    Upotrebu operatora ilustrujemo na primeru klase Razlomak, jer su opera-cije koje se izvode nad skupom razlomaka (racionalnih brojeva) svima bliske anijedan programski jezik nema ugraen tip podataka koji predstava razlomak.

    Definximo binarni operator + kojim realizujemo operaciju sabiraa dvaRazlomka. Rezultat je, u skladu sa pravilima sabiraa racionalnih brojeva,takoe Razlomak.

    public static Razlomak operator +(Razlomak a, Razlomak b)

    {Razlomak r = new Razlomak();

    r.imenilac = a.imenilac * b.imenilac;

    r.brojilac = a.brojilac * b.imenilac + b.brojilac * a.imenilac;

    r.skrati();

    return r;

    }

    Operacije ne meaju operande ve kreiraju rezultat u zavisnosti od vre-dnosti operanada. Zato na poqetku metode kreiramo novi Razlomak r koji e

  • 34 S. Matkovi, M. urixi

    predstavati rezultat, a egove atribute postavamo u skladu sa matematiqkimpravilima sabiraa razlomaka. Radi jednostavnije realizacije pri sabiraune traimo NZS imenilaca ve operande dovodimo na zajedniqki imenilac ko-ji predstava proizvod polaznih imenilaca, pa izvrximo potrebno sabirae.Zatim Razlomak r dovodimo u neskrativ oblik, deeem brojioca i imeniocaihovim NZD, xto je realizovano metodom skrati.

    Ako u klasi Razlomak napixemo konstruktor koji na osnovu datog brojioca iimenioca inicijalizuje atribute objekta tako da on predstava pravi razlomak(brojilac i imenilac uzajamno prosti brojevi) operator + moemo definisatina sledei naqin.

    public static Razlomak operator +(Razlomak a, Razlomak b)

    {return new

    Razlomak(a.brojilac * b.imenilac + b.brojilac * a.imenilac,

    a.imenilac * b.imenilac);

    }

    Operatori kao i sve druge metode mogu se preopteretiti, tako da moemopisati vixe operatora istog imena sa razliqitom listom parametara. Pretho-dno definisanim operatorom realizovana je operacija sabiraa dva razlomka.Qesto je potrebno i sabirae objekta klase Razlomak i celog broja, pa moemodefinisati operator + sa parametrima redom Razlomak, int kao i operator +sa parametrima redom int, Razlomak. Prilikom realizacije metoda operator+(Razlomak a, int b) kreiramo novi razlomak b/1 od celog broja b, a zatimkorixeem operatora + za sabirae dva razlomka saberemo taj razlomak irazlomak a.

    public static Razlomak operator +(Razlomak a, int b)

    {return a + new Razlomak(b,1);

    }

    Korixeem prethodno definisanog operatora + moemo definisati i sa-birae celog broja i objekta klase Razlomak na sledei naqin.

    public static Razlomak operator +(int b,Razlomak a)

    {return a + b;

    }

    Sliqno moemo definisati i ostale operatore za rad sa racionalnim bro-jevima, oduzimae, mnoee, deee. I te operatore moramo preopteretiti nasliqan naqin ako elimo da omoguimo izvoee operacija izmeu razlomaka icelih brojeva.

    Deee dva razlomka moemo realizovati kao mnoee razlomka egovomreciproqnom vrednoxu. Zato je potrebno definisati operator za odreivaereciproqne vrednosti, to je unarni operator koji jednostavno realizujemo:

  • Mala xkola objektno orijentisanog programiraa 35

    public static Razlomak operator ~(Razlomak a)

    {return new Razlomak(a.imenilac, a.brojilac);

    }

    Pomou operatora moemo omoguiti i konverziju objekata klase (tipa po-dataka) koju definixemo u objekte druge klase ili u podatke osnovnog tipa kaoi obrnuto.

    Konverzija se definixe kao unarni operator. Ime tog operatora je ime tipau koji se vrxi konverzija parametra operatora. Parametar operatora ili tipu koji se vrxi konverzija, ali ne oba, moraju biti iz klase u kojoj definixemokonverziju.

    Konverzija moe biti implicitna ili eksplicitna. Prilikom raqunaavrednosti izraza da bi svi podaci u izrazu bili istog tipa vrxi se automatskiihova implicitna konverzija (bez eksplicitnog navoee od strane programe-ra). Implicitnom konverzijom ne dolazi do gubitka informacija pa se moebezbedno pozivati i bez znaa programera.

    Eksplicitnu konverziju programer zahteva dodatnim kodom, korixeemoperatora cast. Prilikom eksplicitne konverzije moe doi do gubitka in-formacija.

    Zaglava implicitnog i eksplicitnog operatora konverzije u C# izgledajuovako:

    public static implicit operator TipRezultata(TipParametra parametar)

    public static explicit operator TipRezultata(TipParametra parametar)

    Svaki ceo broj moemo tumaqiti kao racionalan broj pa je mogue defini-sati implicitnu konverziju iz podatka tipa int u objekat klase Razlomak.

    public static implicit operator Razlomak(int i)

    {return new Razlomak(i,1);

    }

    S druge strane, za svaki razlomak moemo odrediti egovu taqnu ili pri-blinu decimalnu vrednost, xto znaqqi da pri konverziji iz razlomka u realanbroj moe doi do gubitka informacija. Zato je prirodno definisati ekspli-citnu konverziju iz klase Razlomak u osnovni tip double.

    public static explicit operator double(Razlomak r)

    {return (double)r.brojilac / r.imenilac;

    }

    Definisaem operatora implicitne konverzije gubi se potreba za preopte-reenim operatorima kojima omoguavamo izvoee operacija izmeu objekataklase Razlomak i celih brojeva. U sledeem segmentu naredbi C# prikazana je

  • 36 S. Matkovi, M. urixi

    upotreba implicitnog i eksplicitnog operatora konverzije. U naredbi c = a +5 prilikom raqunaa vrednosti izraza ceo broj 5 se automatski (implicitnomkonverzijom) prevodi u razlomak pa se izvrxava operacija sabiraa izmeu dvarazlomka. U naredbi x = (double)a + 5 korixeem cast operatora (double)Razlomak a se konvertuje eksplicitnom konverzijom u realan broj pa se vrxioperacija sabiraa izmeu realnih brojeva.

    Razlomak a=new Razlomak(3,4), b=new Razlomak(textBox1.Text), c;

    double x;

    c = a + 5;

    x = (double)a + 5;

    b = a / 4 - 3;

    x = (double)(a + b);

    Radi boeg sagledavaa svih komponenti klase Razlomak navodimo celu kla-su.

    public class Razlomak

    {#region Atributi

    int imenilac;

    int brojilac;

    # endregion

    #region Konstruktori

    public Razlomak()

    {imenilac = 1;

    brojilac = 0;

    }public Razlomak(int br)

    {brojilac = br;

    imenilac = 1;

    }public Razlomak(int br, int im)

    {if (im = = 0)

    throw new Exception("Greska: imenilac0");

    brojilac = br;

    imenilac = im;

    if (imenilac < 0)

    {brojilac=-brojilac;

    imenilac=-imenilac;

    }skrati();

  • Mala xkola objektno orijentisanog programiraa 37

    }public Razlomak(string s)

    {int p = s.IndexOf(/);

    if (p != -1)

    {brojilac = Convert.ToInt32(s.Substring(0, p));

    imenilac = Convert.ToInt32(s.Substring(p + 1));

    if (imenilac = = 0) throw new Exception("Greska: imenilac 0");

    this.skrati();

    }else

    {brojilac = Convert.ToInt32(s);

    imenilac = 1;

    }}private static int nzd(int a, int b)

    {if (b = = 0)

    return a;

    return

    nzd(b, a % b);

    }private void skrati()

    {int p = nzd(Math.Abs(brojilac), Math.Abs(imenilac));

    imenilac /= p;

    brojilac /= p;

    }#endregion

    #region Operatori

    public static Razlomak operator +(Razlomak a, Razlomak b)

    {return new Razlomak(a.brojilac * b.imenilac + b.brojilac * a.imenilac, a.imenilac

    * b.imenilac);

    }public static Razlomak operator -(Razlomak a)

    {return new Razlomak(-a.brojilac, a.imenilac);

    }public static Razlomak operator -(Razlomak a, Razlomak b)

    {return a + (-b);

    }

  • 38 S. Matkovi, M. urixi

    public static Razlomak operator *(Razlomak a, Razlomak b)

    {return new Razlomak(a.brojilac * b.brojilac, a.imenilac * b.imenilac);

    }public static Razlomak operator (Razlomak a)

    {return new Razlomak(a.imenilac, a.brojilac);

    }public static Razlomak operator /(Razlomak a, Razlomak b)

    {return a * b;

    }public static explicit operator double(Razlomak r)

    {return (double)r.brojilac / r.imenilac;

    }public static implicit operator Razlomak(int i)

    {return new Razlomak(i, 1);

    }public static bool operator >(Razlomak A, Razlomak B)

    {return A.brojilac * B.imenilac > B.brojilac * A.imenilac;

    }public static bool operator

  • Mala xkola objektno orijentisanog programiraa 39

    klase A koji predstava vreme trajaa filma i objekat iste klase B koji pred-stava vreme trajaa filmskog urnala i reklama, sabiraem ta dva vremenase moe dobiti vreme trajaa bioskopske projekcije, C. Ako bismo napisalioperator + za klasu Vreme mogli bismo vreme C da odredimo sledeim pozivomtog operatora:

    C = A+B;

    Operator sabiraa moemo definisati na sledei naqin:

    public static Vreme operator+(Vreme A, Vreme B)

    {return new Vreme(A.sekunde+B.sekunde);

    }

    Na sliqan naqin moemo definisati i operatore:

    public static Vreme operator +(Vreme a,int b)operator za odreivae zbira vremena a i broja sekundi b

    public static Vreme operator -(Vreme a, Vreme b)operator za odreivae apsolutne razlike vremena a i b

    public static bool operator >(Vreme a, Vreme b)operator za proveru da li vreme a traje due od vremena b

    public static bool operator

  • 40 S. Matkovi, M. urixi

    #region Konstruktori

    public Datum()

    {dan = 1;

    mesec = 1;

    godina = 2010;

    }

    public Datum(Datum D)

    {godina = D.godina;

    mesec = D.mesec;

    dan = D.dan;

    }

    public Datum(string s)

    {dan = Convert.ToInt32(s.Substring(0,s.IndexOf(.)));

    s=s.Remove(0, s.IndexOf(.) + 1);

    mesec = Convert.ToInt32(s.Substring(0, s.IndexOf(.)));

    godina = Convert.ToInt32(s.Substring(s.IndexOf(.) + 1));

    }

    public Datum(int d, int m, int g)

    {godina = g;

    mesec = m;

    dan = d;

    }#endregion

    . . .

    }

    U ovako realizovanoj klasi moemo definisati raznovrsne operatore. Je-dan od interesantnijih operatora je unarni operator koji obezbeuje prelazaku sledei dan, odnosno odreivae sutraxeg datuma. Realizovaemo ga kaooperator++:

    public static Datum operator ++(Datum D)

    {int d = D.dan + 1;

    int m = D.mesec;

    int g = D.godina;

    // statiqkim metodom brDana(m,g)

    // odreujemo broj dana u mesecu m godine g

    if (d > brDana(m, g))

    {

  • Mala xkola objektno orijentisanog programiraa 41

    d = 1;

    m++;

    if (m == 13)

    {m = 1;

    g++;

    }}return new Datum(d, m, g);

    }

    Ovaj operator predefinixe poznati operator uveavaa za 1 iz programskogjezika C pa je i egovo korixee u skladu sa tim. Naime, ovaj operator kao iemu srodni operator -- moe se pozivati i u prefiksnoj i u postfiksnoj nota-ciji. On pri svakom pozivu mea vrednost parametra dodeujui mu povratnuvrednost ali je vrednost samog izraza ++ jednaka staroj vrednostiparametra, dok je vrednost izraza ++ jednaka novoj vrednosti.

    Moemo primetiti da u klasi Datum nema smisla definisati operator kojimse sabiraju dva objekta klase Datum ali se moe definisati operator kojim sena objekat klase Datum moe dodati ceo broj dana. Takoe, od datuma moemooduzimati izvestan ceo broj dana ali se moe odrediti i broj dana izmeu dvadatuma.

    public static Datum operator +(Datum a,int b) public static Datrum operator -(Datrum a, int b) public static int operator -(Datum a, Datum b)Realizaciju ovih operatora prepuxtamo qitaocu.

    Smisleno je i predefinisati operatore poreea dva datuma kako bi seutvrdilo koji je datum pre a koji posle (operatori < i >) kao i da li su dvadatuma ista, odnosno razliqita (== i !=). Predefinisaem operatora == gubimoegovo uobiqajeno znaqee poreea referenci dva objekta i definixemo novo.U klasi Datum operatore == i != moemo definisati tako da porede datume povrednosti atributa.

    public static bool operator==(Datum a, Datum b)

    {return a.godina==b.godina && a.mesec==b.mesec && a.dan==b.dan;

    }public static bool operator!=(Datum a, Datum b)

    {return !(a==b);

    }

    Kada govorimo o bilo kom dogaaju meu najznaqajnijim informacijama suinformacije koje govore o tome kada se taj dogaaj odvija. Kako bismo takveinformacije precizno zapisali neophodno je da imamo podatke i o datumu i o

  • 42 S. Matkovi, M. urixi

    vremenu. Moemo definisati klasu VremenskiTrenutak qije objekte opisujuatributi D, tipa Datum i V , tipa Vreme. Ova klasa je naroqito interesantnazbog operatora koje moemo realizovati u oj.

    public static VremenskiTrenutak operator +(VremenskiTrenutak a,Vreme b)

    odreivae trenutka koji je za vreme b posle trenutka a

    public static Vreme operator -(VremenskiTrenutak a,VremenskiTrenutak b)

    odreivae vremena izmeu dva trenutka

    public static VremenskiTrenutak operator -( VremenskiTrenutak a,Vreme b)

    odreivae trenutka koji je za vreme b pre trenutka a

    public static bool operator (VremenskiTrenutak a,VremenskiTrenutak b)

    public static bool operator ==( VremenskiTrenutak a,VremenskiTrenutak b)

    public static bool operator !=( VremenskiTrenutak a,VremenskiTrenutak b)

    Klase Vreme, Datum i VremenskiTrenutak su vrlo upotrebive u velikombroju aplikacija ali i kao atributi brojnih sloenijih klasa. Recimo da jedefinisana klasa Manifestacija koja za atribute ima naziv, mesto odravaa,poqetak (tipa VremenskiTrenutak) i duinu trajaa (tipa Vreme). Neka je zadatraspored korisnika sa vremenom boravka u razliqitim mestima. Moemo kre-irati aplikaciju kojom se na osnovu dostupnih informacija moe predloitikorisniku koje sve manifestacije moe da poseti, tako da ne poremeti svoj ras-pored. Pri kreirau takve aplikacije definisani operatori bi doprineli je-dnostavnosti realizacije.

    Predlaemo qitaocu da u potpunosti realizuje ove klase sa svim navedenim,ali i nenavedenim, a smislenim operatorima kao i xto vixe aplikacija u kojimase korisno mogu upotrebiti.

    Klasa Polinom

    Ilustrujmo definisae operatora u klasi koja kao atribut ima niz. Posma-trajmo klasu za rad sa polinomima. Polinom moemo opisati stepenom i nizomkoeficijenata, ili nizom monoma kod kojih su koeficijenti razliqiti od nule.Radi jednostavnije realizacije u navedenoj klasi polinom je opisan stepenom (n)i nizom koeficijenata (k) tako da i-ti element niza k (k[i]) predstava koefi-cijent uz i-ti stepen polinoma. U klasi Polinom moemo definisati operatore(+, -, *, /) za izvoee osnovnih aritmetiqkih operacija nad objektima klase.

  • Mala xkola objektno orijentisanog programiraa 43

    public class Polinom

    {float[] k;// niz koeficijenata polinoma

    int n; // stepen polinoma

    // podrazumevani konstruktor za formirae nula polinoma

    public Polinom()

    {n = 0;

    k = new float[1];

    k[0] = 0;

    }// konstruktor kojim se formira polinom stepena n

    // sa koeficijentima jednakim 0

    public Polinom(int n)

    {this.n = n;

    k = new float[n+1];

    for(int i=0;i

  • 44 S. Matkovi, M. urixi

    return c;

    }}

    Navodimo nekoliko interesantnih klasa na kojima moemo ilustrovati ope-ratore:

    klasa za rad sa kompleksnim brojevima (obezbediti i grafiqki prikaz objek-ta klase). U okviru te klase mogu se realizovati operatori za sabirae, od-uzimae, mnoee, deee dva kompleksna broja, odreivae konjugovanogkompleksnog broja (unarni operator npr. ), odreivae modula kompleksnogbroja, operator implicitne konverzije iz realnog u kompleksni broj.

    klasa za rad sa vektorima (obezbediti i grafiqki prikaz objekata klase) klasa kojom realizujemo aritmetiku velikih brojeva (brojeva sa proizvonomnogo cifara). Mogu se postepeno razvijati klase za rad sa velikim bro-jevima polazei od prirodnih brojeva, zatim razvoj klase za rad sa celimbrojevima i na kraju sa velikim realnim brojevima. Veliki ceo broj moemoopisati znakom i nizom cifara (znak i apsolutna vrednost broja), a moemoi nizom cifara koji predstava zapis broja u potpunom komplementu osnove10. U ovim klasama prirodno je realizovati sve aritmetiqke operatore kaoi operatore poreea.

    klasa za rad sa skupovima (realizovati operatore unija, presek, razlika).

    Matematiqka gimnazija, Kraice Natalije 37, Beograd

  • NASTAVA RAQUNARSTVA

    Stanka Matkovi, Mijodrag urixi

    MALA XKOLA OBJEKTNO ORIJENTISANOGPROGRAMIRAA U PROGRAMSKOM JEZIKU C#

    Trei deo

    Nasleivae prvi deo

    Nasleivae je jox jedna vana osobina objektno orijentisanih programskihjezika. Ona je posledica generalizacije kao metoda za modelovae objekata.

    Setimo se primera nastavnog procesa iz prvog dela ,,Male xkole OOP uprogramskom jeziku C#. U nastavnom procesu uqestvuju uqenici, profesori,psiholog, direktor, . . . Svi oni imaju neke zajedniqke karakteristike ali i svo-je specifiqnosti. Svi uqesnici u nastavnom procesu imaju svoje ime, prezime,datum i mesto roea, adresu stanovaa, . . . Generalizacijom dolazimo do klase(nazovimo je Osoba) koja objediuje zajedniqke osobine i zajedniqke funkcional-nosti svih posebnih grupa koje uqestvuju u nastavnom procesu.

    Svaka grupa ima i svoje specifiqne osobine, kao i specifiqno ponaxae unastavnom procesu. Za uqenika su, pored karakteristika opisanih klasom Osoba,vane i informacije o razredu koji pohaa, o predmetima koje sluxa, o rezulta-tima koje postie ali i akcije koje izvodi u nastavnom procesu (uqi lekciju, radipismeni zadatak, odgovara, . . . ). Sliqno, za profesora moemo uoqiti niz doda-tnih karakteristika (predmete koje predaje, godine staa, platni razred, . . . )kao i niz specifiqnih funkcionalnosti u nastavnom procesu (predaje lekciju,oceuje, . . . ). Operaciju izvoea posebnih klasa iz opxte (generalizovane)klase zovemo specijalizacija.

    Klase dobijene specijalizacijom, osim xto nasleuju sve qlanove (atributei metode) polazne klase, definixu i nove, specifiqne qlanove. Polaznu klasuzovemo osnovna klasa (roditeska klasa, nadklasa), a klasu koja je nasleujezovemo izvedena klasa (podklasa).

    U izvedenoj klasi definixemo samo atribute i metode specifiqne za tu kla-su (eventualno predefinixemo metode osnovne klase) ali eni objekti nasleujui sve qlanove osnovne klase. Izvedena klasa proxiruje, a u nekim sluqajevimai precizira osnovnu klasu.

    U definiciji izvedene klase posle navoea imena klase navodimo : azatim sledi ime osnovne klase iz koje je izvedena.

  • Mala xkola objektno orijentisanog programiraa 43

    class :

    {opis / definicija clanova klase

    }

    U programskom jeziku C# klasa moe naslediti samo jednu osnovnu klasu,odnosno ne moe nastati kao specijalizacija dve ili vixe klasa. Takoe, izvede-na klasa ne moe naslediti klasu koja sadri modifikator sealed. Ako elimoda definixemo klasu iz koje se ne mogu izvoditi druge klase modifikator sealednavodimo u zaglavu klase ispred slubene reqi class.

    Vano je napomenuti da u izvedenoj klasi, bez obzira xto nasleuje sve qla-nove osnovne klase, ne moemo pristupiti privatnim qlanovima osnovne klase.Da se ne bi naruxila enkapsulacija atributi osnovne klase ne treba da budujavni a ako su privatni onda im se ne moe pristupiti iz izvedene klase. Zatopostoji i trei nivo pristupa qlanovima klase zaxtieni (engl. protected).Zaxtieni qlanovi klase dostupni su u klasi u kojoj su definisani i u svimklasama izvedenim iz te klase, a izvan ih nisu. Prema tome, iz izvedene kla-se moe se pristupiti javnim i zaxtienim qlanovima osnovne klase, ali ne iprivatnim.

    Da bi bio kreiran objekat izvedene klase mora se prvo kreirati egov osnov-ni, bazni deo sa atributima definisanim u osnovnoj klasi. Za kreirae objektaosnovne klase zaduen je konstruktor osnovne klase. Zato se u konstruktoru izve-dene klase implicitno (automatski) poziva konstruktor bez argumenata osnovneklase osim ako programer eksplicitno ne navede koji konstruktor osnovne klasepoziva prilikom kreiraa objekta. Poziv konstruktora osnovne klase programerrealizuje tako xto posle potpisa konstruktora izvedene klase navede dve taqke(:) a zatim slubenu req base i u zagradama redom parametre konstruktoraosnovne klase kojeg pozivamo.

    public class Osnovna {// ....

    public Osnovna()

    {// ....

    }public Osnovna(int x)

    {// ....

    }//...

    }public class Izvedena:Osnovna

    {// ....

    public Izvedena()

  • 44 S. Matkovi, M. urixi

    {//....

    }public Izvedena(int a,int s):base(a)

    {// ...

    }//...

    }

    Izvedena klasa je nasleivaem dobila sve atribute i metode osnovne klasepa objekat izvedene klase sadri sve qlanove kao i objekat osnovne klase. Zato seobjekat izvedene klase, bez eksplicitne konverzije, moe dodeliti promenivojosnovne klase. Obrnuto nije dozvoeno jer objekat osnovne klase ne sadri sveelemente izvedene klase. Vano je istai da preko promenive osnovne klasekojoj smo dodelili objekat izvedene klase moemo pozivati samo qlanove osnovneklase.

    Ako su A i B promenive, redom osnovne i izvedene klase, dozvoena jedodela A = B. Posle te dodele preko promenive A moemo pozivati samoqlanove osnovne klase. Nije dozvoena dodela B = A jer je A promenivaosnovne klase (sadri samo qlanove osnovne klase) pa specifiqni qlanovi koje bitrebalo da ima objekat izvedene klase, B, ne mogu biti definisani tom dodelom.

    U izvedenoj klasi moemo, osim potpuno novih metoda, definisati i metodekoje po imenu, povratnom tipu i po argumentima (po tipu, broju i redosleduargumenata) odgovaraju metodima osnovne klase. Moemo rei da ti metodi uizvedenoj klasi ,,kriju odgovarajue metode osnovne klase. Skrivenom qlanuosnovne klase u izvedenoj klasi moemo pristupiti samo ako ispred imena qlanadodamo slubenu req base i taqku (.).

    public class Osnovna

    {// ....

    public void radi()

    {// ....

    }public string pisi()

    {// ....

    }//...

    }public class Izvedena:Osnovna

    {// ....

  • Mala xkola objektno orijentisanog programiraa 45

    new public void radi()

    {base.radi();

    //....

    }public string pisi()

    {return base.pisi()+...;

    }//...

    }

    Ako u izvedenoj klasi definixemo metod istog zaglava kao u osnovnoj klasi(sa ili bez modifikatora new ispred zaglava) onda taj metod moemo pozvatisamo kao metod promenive izvedene klase (new se navodi da bi se kompajalerustavilo do znaa da smo namerno, a ne sluqajno, zaklonili metodu bazne klase;ako se ne navede, kompajler upozorava programera).

    Izvedena B = new Izvedena();

    Text=B.Pisi(); B.radi();//pozivaju se metodi klase Izvedena

    Ako objekat deklarixemo kao objekat osnovne klase pozivom metoda emopristupati metodu osnovne klase qak iako objekat kreiramo kao objekat izvedeneklase.

    Osnovna A = new Izvedena();

    A.radi();//poziva se metod klase Osnovna

    Qesto se dexava da metode imaju istu svrhu ali se razliqitio realizujuu razliqitim izvedenim klasama. U klasama izvedenim iz klase Osoba metodza prikaz informacija o osobi razliqito se realizuje jer u svakoj klasi imamododatne informacije, a metod za proveru da li je osoba starija od druge osobeili metod za promenu adrese osobe u svim klasama se realizuju na isti naqin.Da bismo mogli predefinisati metod u izvedenoj potrebno je u osnovnoj klasiproglasiti metod virtuelnim, navoeem slubene reqi virtual u zaglavumetoda, pre navoea povratnog tipa metoda. U izvedenoj klasi pri definicijipredefinisanog metoda treba navesti slubenu req override.

    public class Osnovna

    {// ....

    public virtual void radi()

    {// ....

    }public virtual string pisi()

    {

  • 46 S. Matkovi, M. urixi

    // ....

    }//...

    }public class Izvedena:Osnovna

    {// ....

    public override void radi()

    {//....

    }//...

    }

    Poziv virtuelnog metoda se vrxi na osnovu tipa objekta koji promenivasadri a ne na osnovu tipa promenive.

    Osnovna A = new Izvedena();

    A.radi();//poziva se metod klase Izvedena

    Predefinisae virtuelnih metoda u jednoj ili vixe izvedenih klasa moebiti izostaveno. Tada se za objekte tih klasa poziva odgovarajui metod izklase koja je u hijerarhiji klasa najblia klasi objekta.

    Osnovna A = new Izvedena();

    Text=A.pisi();//poziva se metod klase Osnovna

    Izbor virtuelnog metoda koji se poziva vrxi se u toku izvrxavaa, a ne utoku prevoea, korixeem tehnike dinamiqkog povezivaa.

    Metod ToString() je virtuelni metod klase object koja je osnovna klasa zasve klase realizovane u C#. Zato u svakoj C# klasi imamo mogunost prede-finisaa ovog metoda. Ako ga ne predefinixemo, virtuelni metod klase objectvraa pun naziv klase u kojoj je objekat kreiran.

    Virtuelne metode omoguavaju da promeniva osnovne klase, u zavisnostiod klase qiji joj je objekat dodeen, isti metod izvrxava na razliqite naqi-ne (korixeem predefinisanog (engl. override) metoda iz izvedene klase kojojobjekat pripada). Tu osobinu objektno orijentisanog programiraa zovemo po-limorfizam (pojavivae u vixe oblika).

    Osnovna A = new Osnovna();

    A.radi();//poziva se metod klase Osnovna

    A = new Izvedena();

    A.radi();//poziva se metod klase Izvedena

    Promeniva A je promeniva klase Osnovna. Kada joj dodelimo objekatiste klase poziv metoda A.radi() izvrxava virtuelni metod radi() iz klaseOsnovna. Kada promenivoj A dodelimo objekat klase Izvedena istim pozivomizvrxava se predefinisani (override) metod radi() iz klase Izvedena.

  • Mala xkola objektno orijentisanog programiraa 47

    Zahvaujui polimorfizmu moemo jednostavno kreirati aplikacije kojerade na razliqitom hardveru i u razliqitim operativnim sistemima. Progra-mer moe pozivati odreene metode bez osvrtaa na naqin ihove realizacije.Zamislimo da iz aplikacije treba xtampati dokument. Programer e pri kodi-rau pozvati odgovarajui metod (recimo Print) aktivnog xtampaqa bez obzirakoji je model u pitau. Taj metod je razliqito realizovan za svaki model po-naosob, ali programer ne mora da razmixa o naqinu realizacije jer je svakixtampaq objekat neke od izvedenih klasa iz osnovne klase (npr. Printer). Uosnovnoj klasi je definisana virtuelna metoda Print koja je u izvedenim klasa-ma predefinisana.

    Primer 1. Osoba

    U ovom primeru navexemo uproxenu realizaciju osnovne klase Osoba iizvedenih klasa Ucenik i Profesor, i jednu jednostavnu aplikaciju kao ilu-straciju prethodnog teksta. Sledei dijagram prikazuje hijerarhiju klasa uprimeru:

    U realizaciji navedenih klasa, koja sledi, komentarima su objaxeni delo-vi koda koji se odnose na nasleivae.

    public class Osoba//osnovna klasa

    {string ime, prezime;

    int brGodina;

    string adresa;

    public Osoba (string ime, string prezime,int brGodina, string adresa)

    {this.ime = ime;

    this.prezime = prezime;

    this.brGodina = brGodina;

    this.adresa = adresa;

    }public Osoba()

    {ime = prezime =adresa="";

    brGodina = 0;

    }public Osoba(Osoba X)

  • 48 S. Matkovi, M. urixi

    {ime = X.ime;

    prezime = X.prezime;

    brGodina = X.brGodina;

    adresa = X.adresa;

    }// virtuelna metoda

    public virtual string informacije()

    {return ime + " " + prezime;

    }// nema potrebe da metodi koji slede budu virtuelni

    //jer se jednako realizuju kod svih osoba

    public bool starijaOd(Osoba B)

    {return brGodina > B.brGodina;

    }public void promenaAdrese( string novaAdresa)

    {adresa = novaAdresa;

    }}

    public class Ucenik : Osoba

    {int razred;

    int []ocene;

    public Ucenik():base()

    // nije neophodno eksplicitno pozvati konstruktor bazne klase,

    // jer ako ne pozovemo nijedan konstruktor bazne klase automatski se

    // poziva podrazumevani konstruktor, tj. konstruktor bez argumenata

    {razred = 1;

    ocene=newint[15];

    }public Ucenik(string uIme, string uPrezime, int uBrGod, string uAdresa, int uRaz)

    : base(uIme, uPrezime,uBrGod,uAdresa)

    //poziv odgovarajuceg baznog konstruktora

    {razred = uRaz;

    ocene = newint[15];

    }public Ucenik(Ucenik U)

    : base(U)

    // base(U) poziv konstruktora kopije bazne klase

    // bez obzira sto je parametar konstruktora kopije bazne klase promenljiva tipa

  • Mala xkola objektno orijentisanog programiraa 49

    // Osoba, poziv konstruktora kopije klase Osobe sa argumentom U koji je objekat

    // izvedene klase Ucenik je ispravno jer je dozvoljeno promenljivoj bazne

    // klase dodeliti objekat izvedene klase

    {razred = U.razred;

    ocene=newint [U.ocene.Length];

    for (int i = 0; i < U.ocene.Length; i++) ocene[i] = U.ocene[i];

    }//predefinisanje viruelnog metoda

    public override string informacije()

    {returnbase. informacije ()+ " " + razred;

    //poziva se metod osnovne klase

    }}

    public class RedovanUcenik : Ucenik

    {char odeljenje;

    int brojIzostanaka; public RedovanUcenik():

    base()

    {odeee = ;

    brojIzostanaka = 0;

    }public RedovanUcenik(string rIme, string rPrezime, int rBrGod,

    string rAdresa, int rRaz,char rOdeljenje)

    : base(rIme,rPrezime,rBrGod,rAdresa,rRaz)

    {odeljenje = rOdeljenje;

    brojIzostanaka =0;

    }public RedovanUcenik(RedovanUcenik r): base(r)

    {odeljenje = r.odeljenje;

    brojIzostanaka = r.brojIzostanaka;

    }public override string informacije()

    {returnbase. informacije ()+" "+odeljenje+" "+brojIzostanaka;

    //bazna klasa za klasu RedovanUcenik je klasa Ucenik

    }// Mozemo dodati metode karakteristicne za redovnog ucenika

    // na primer ocenjivanje ucenika, dodavanje izostanaka, izracunavanje proseka

    }public class VanredanUcenik : Ucenik

  • 50 S. Matkovi, M. urixi

    {DateTime []datumPolagaa;

    public VanredanUcenik(): base()

    {datumPolaganja=new DateTime[15];

    }public VanredanUcenik(string vIme, string vPrezime, int vBrGod,

    string vAdresa, int vRaz)

    : base(vIme, vPrezime,vBrGod, vAdresa, vRaz)

    {datumPolaganja=new DateTime[15];

    }public VanredanUcenik(VanredanUcenik V)

    : base(V)

    {datumPolaganja = new DateTime[V.datumPolaganja.Length];

    for (int i = 0; i < V.datumPolaganja.Length; i++)

    datumPolaganja[i] = V.datumPolaganja[i];

    }// Mozemo dodati metode karakteristicne za vanrednog ucenika,

    // na primer unos ocene ucenika

    }public class Profesor:Osoba

    {string predmet;

    float koeficijent;

    public Profesor()

    {predmet="";

    koeficijent=0;

    }public Profesor (string ime, string prezime, int brGod,

    string adresa,stringpredmet,float koeficijent)

    : base(ime, prezime, brGod,adresa)

    {this.predmet = predmet;

    this.koeficijent = koeficijent;

    }public Profesor (Profesor z) : base(z)

    {this.predmet = z.predmet;

    this.koeficijent = z.koeficijent;

    }public override string informacije ()

    {

  • Mala xkola objektno orijentisanog programiraa 51

    returnbase. informacije () + " " + predmet + " " + koeficijent;

    }// Mozemo dodati jos metoda karakteristicnih za profesora

    }

    Sledi jednostavna aplikacija u kojoj koristimo prethodno realizovane kla-se. U fajlu skola.txt nalaze se informacije o uqesnicima nastavnog procesa unekoj xkoli (najvixe 1000 uqesnika). Za svakog uqesnika u jednoj liniji je da-ta informacija o vrsti tog uqesnika (da li je redovan uqenik, vanredan uqenikili profesor), a zatim sve potrebne informacije o emu (svaka informacija uposebnoj liniji). Aplikacijom je obezbeen prikaz informacija o svim uqesni-cima nastavnog procesa te xkole qije ime ili prezime, u zavisnosti od izborakorisnika, poqie datim stringom. Obezbeen je i ispis imena i prezimenanajstarije osobe meu prikazanim osobama.

    Sve uqesnike nastavnog procesa, bez obzira xto pripadaju razliqitim kla-sama, moemo objediniti korixeem niza a promenivih osnovne klase Osoba.Dozvoeno je promenivoj osnovne klase dodeliti objekat izvedene klase, takoda svakom elementu niza amoemo dodeliti objekte klase RedovanUcenik, Van-redanUcenik, Profesor.

    Osoba[] a = new Osoba[1000];

    int n = 0;

    Osoba citajOsobu(StreamReader sr)

    {string vrsta = sr.ReadLine();

    Osoba A;

    string ime, prezime,adresa;

    int brGod;

    ime = sr.ReadLine();

    prezime=sr.ReadLine();

  • 52 S. Matkovi, M. urixi

    brGod=Convert.ToInt32(sr.ReadLine());

    adresa=sr.ReadLine();

    if (vrsta == "redovan ucenik")

    A = new RedovanUcenik(ime, prezime, brGod, adresa,

    Convert.ToInt32(sr.ReadLine()), sr.ReadLine()[0]);

    elseif (vrsta == "vanredan ucenik")

    A = new VanredanUcenik(ime, prezime, brGod,adresa,

    Convert.ToInt32(sr.ReadLine()));

    else

    A = new Profesor(ime, prezime, brGod, adresa,

    sr.ReadLine(),Convert.ToSingle(sr.ReadLine()));

    return A;

    }private void Form1 Load(object sender, EventArgs e)

    {StreamReader sr = new StreamReader("skola.txt");

    Osoba max = null;

    while (!sr.EndOfStream)

    {a[n] = citajOsobu(sr);

    lbSpisak.Items.Add(a[n].informacije());

    // metod informacije() je virtuelni i u svakoj izvedenoj klasi je predefinisan

    // pa se u zavisnosti od objekta koji se nalazi u promenljivoj a[n] poziva metod

    // informacije() iz odgovarajuce klase

    if (max == null || a[n].starijaOd(max))

    //poziv metoda starijaOd definisanog u klasi Osoba

    max = a[n];

    n++;

    }sr.Close();

    if (max != null)

    {lbSpisak.Items.Add("* * * * * * * *");

    lbSpisak.Items.Add("najstarija osoba je ");

    lbSpisak.Items.Add(max.Ime+ " "+max.Prezime);

    }}

    private void tbIme TextChanged(object sender, EventArgs e)

    {string s = tbIme.Text.ToLower();

    lbSpisak.Items.Clear();

    Osoba max = null;

    for (int i = 0; i < n; i++)

    {if((rbIme.Checked && a[i].Ime.ToLower().StartsWith(s))||

  • Mala xkola objektno orijentisanog programiraa 53

    (rbPrezime.Checked && a[i].Prezime.ToLower().StartsWith(s)))

    // koriscenje svojstava Ime i Prezime definisanih u klasi Osoba

    {lbSpisak.Items.Add(a[i].informacije());

    // poziv metoda informacije() iz odgovarajuce klase

    if (max == null || a[i].starijaOd(max))

    //poziv metoda starijaOd definisanog u klasi Osoba

    max = a[i];

    }}

    if (max != null)

    {lbSpisak.Items.Add("* * * * * * * *");

    lbSpisak.Items.Add("najstarija osoba je ");

    lbSpisak.Items.Add(max.Ime + " " + max.Prezime);

    }}

    Matematiqka gimnazija, Kraice Natalije 37, Beograd

  • NASTAVA RAQUNARSTVA

    Stanka Matkovi, Mijodrag urixi

    MALA XKOLA OBJEKTNO ORIJENTISANOGPROGRAMIRAA U PROGRAMSKOM JEZIKU C#

    Qetvrti deo

    Nasleivae, drugi deo apstraktne klase

    U posledem primeru qlanka iz prethodnog broja mogli smo zakuqiti daje svaki uqesnik nastavnog procesa objekat neke od klasa Ucenik ili Profesor.Ne postoji uqesnik nastavnog procesa koji je objekat klase Osoba, pa moemorei da klasa Osoba samo postoji da bi objedinila zajedniqke karakteristike ifunkcionalnosti objekata izvedenih klasa.

    Pri procesu generalizacije, izdvajaem zajedniqkih osobina i funkcional-nosti nekoliko srodnih klasa, moemo kreirati klasu na vixem nivou apstrak-cije koja se ne materijalizuje kroz objekte (ne kreiramo ene objekte). Takvuklasu zovemo apstraktnom klasom. Pri enoj definiciji neophodno je pre imenaklase navesti modifikator abstract.

    abstract public class Osnovna

    {// clanovi klase

    }

    Apstraktna klasa je nepotpuna. Neophodno je iz e izvoditi klase qijeemo objekte kreirati i definisati ihovo ponaxae. U apstraktnoj klasinavodimo zajedniqke funkcionalnosti svih izvedenih klasa, koje u izvedenimklasama moemo predefinisati. Naravno, svaka od izvedenih klasa moe imatineke svoje specifiqne funkcionalnosti.

    Vrlo qesto u klasi koja je dobijena generalizacijom ne moemo realizovatizajedniqku funkcionalnost koju svaka od izvedenih klasa ima ali se u svakoj odih realizuje na razliqit naqin. Polazei od oblika poput kruga, pravougaoni-ka, kvadrata, trougla generalizacijom dolazimo do klase Oblik, a specijaliza-cojom iz te klase razvijamo klase Krug, Kvadrat, Pravougaonik, Trougao. Svakioblik se moe nacrtati, i za svaki oblik moemo izraqunati obim i povrxinu,ali u klasi Oblik ne moemo realizovati te metode. Potrebno je da klasa Ob-lik ima te funcionalnosti da bi, korixeem polimorfizma, svakom elementu

  • Mala xkola objektno orijentisanog programiraa 33

    skupa razliqitih oblika mogli uputiti zahtev da ih izvrxi. Svaki element ena zahtev (Crtaj, Povrsina, Obim) odgovoriti na sebi svojstven naqin.

    Metod apstraktne klase za koji dajemo samo deklaraciju a ne i definiciju,naziva se apstraktni metod. Apstraktni metod pixemo navoeem modifikatoraabstract ispred deklaracije metoda koju zavrxavamo taqka zarezom. Pri dekla-raciji apstraktnog svojstva moramo navesti da li je to get i/ili set svojstvo.

    abstract public povratniTip imeMetoda(listaParametara);

    abstract public povratniTip imeSvojstva

    {get;

    set;

    }

    U klasama koje su izvedene iz apstraktne klase pri realizaciji apstraktnihqlanova modifikator abstract zameujemo slubenom reqi override. Ako uizvedenoj klasi nismo realizovali sve apstraktne qlanove i ta izvedena klasa jeapstraktna pa je potrebno pri enoj definiciji navesti modifikator abstract.

    Primer 2. Oblik.

    Navodimo realizaciju apstraktne klase Oblik i iz e izvedenih klasa Krug,Pravougaonik, Kvadrat i JednakostranicniTrougao. Posmatramo pojednostav-ene oblike, kod kvadrata i pravougaonika stranice su paralelene koordinatnimosama, a kod jednakostraniqnog trougla jedna stranica je paralelna x-osi.

    U osnovnoj klasi Oblik definixemo zajedniqke (centar i boju oblika) a u iz-vedenim klasama dodatne atribute. Svi oblici imaju sledee funkcionalnosti:odreivae obima, odreivae povrxine, crtae, provera da li oblik sadridatu taqku i pomerae oblika za date vrednosti po x i y osi. Samo posledaod navedenih funkcionalnosti realizuje se na isti naqin u svim klasama, pome-raem centra oblika za date vrednosti. Zato taj metod realizujemo u osnovnojklasi i nema potrebe da ga u izvedenim klasama predefinixemo. Ostale finkci-onalnosti (crtaj, obim, povrsina, sadrzi) ne moemo realizovati u osnovnojklasi dok ne konkretizujemo oblik. Zato su u klasi Oblik ove funkcionalnostiapstraktne, a ihova realizacija se nalazi u izvedenim klasama.

  • 34 S. Matkovi, M. urixi

    Napomenimo da je kvadrat pravougaonik kod kojeg duina i xirina imajuiste vrednosti, pa u skladu sa tim klasu Kvadrat dobijamo specijalizacijom izklase Pravougaonik.

    public abstract class Oblik{

    protected Color boja;protected PointF centar;public Oblik(Color boja, PointF centar)

    {this.boja = boja;this.centar = centar;}

    public Oblik(){this.boja = Color.Black;this.centar = new PointF(0, 0);}

    public void Pomeri(int dx, int dy){centar.X += dx;centar.Y += dy;}

    // apstraktna get svojstva za odre -divanje obima i povrsinepublic abstract float Obim

    { get; }public abstract float Povrsina

    { get; }// apstraktni metod za crtanje oblikapublic abstract void Crtaj(Graphics g);// apstraktni metod za proveru da li oblik sadrzi datu tackupublic abstract bool SadrziTacku(PointF A );

    }public class Krug : Oblik

    {float r;public Krug(Color boja, PointF centar, float r):base(boja, centar)

    {this.r = r;}

    public Krug():base(){this.r = 10;}

    public override void Crtaj(Graphics g){g.FillEllipse(newSolidBrush(base.boja), base.centar.X - r, base.centar.Y - r,

    2 * r, 2 * r);}

    public override float Povrsina{get { return r * r * (float)Math.PI; }}

    public override float Obim{get { return 2 * r * (float)Math.PI; }}

    public override bool SadrziTacku(PointF M){

  • Mala xkola objektno orijentisanog programiraa 35

    return Math.Sqrt((M.X - centar.X) * (M.X - centar.X) + (M.Y - centar.Y) *(M.Y - centar.Y)) = 0;}

    private static floatf(float a, float b, float c, PointF T){return a * T.X + b * T.Y + c;}

    }

  • 36 S. Matkovi, M. urixi

    public class Pravougaonik : Oblik{protectedfloat a, b;public Pravougaonik(Color boja, PointF centar, float a, float b) : base(boja,

    centar){this.a = a;this.b = b;}

    public Pravougaonik() : base(){this.a = this.b = 10;}

    public override void Crtaj(Graphics g){g.FillRectangle(newSolidBrush(base.boja), centar.X-a/2,centar.Y-b/2,a,b);}

    public override float Povrsina{get return a * b;}

    public override float Obim{get { return 2 * a + 2 * b; }}

    public override bool SadrziTacku(PointF M){return(M.X >= centar.X - a / 2)&&(M.X = centar.Y - b / 2)&&(M.Y

  • Mala xkola objektno orijentisanog programiraa 37

    private void pictureBox1 Paint(object sender, PaintEventArgs e){for (int i = 0; i < n; i++)o[i].Crtaj(e.Graphics);}

    private void numericUpDown1 ValueChanged(object sender, EventArgs e){n = (int)numericUpDown1.Value;o = newOblik[n];for (int i = 0; i < n; i++){

    int t = R.Next(1, 5);Color boja = Color.FromArgb(R.Next(200, 256), R.Next(256), R.Next(256), R.Next(256));PointFP=newPointF(R.Next(0,ClientRectangle.Width),R.Next(0,ClientRectangle.Height));switch (t)

    {case 1:

    o[i] = newKrug(boja, P,R.Next(10,20)); break;case 2:

    o[i] = newJednakostranicniTrougao(boja, P, R.Next(20,50)); break;case 3:

    o[i] = newPravougaonik(boja,P, R.Next(10,50),R.Next(10,50)); break;case 4:

    o[i] = newKvadrat(boja, P, R.Next(10, 50)); break;}}pictureBox1.Refresh();// aktivira metodu pictureBox1 Paint}

    private void pictureBox1 MouseDown(object sender, MouseEventArgs e){x = e.X;y = e.Y;PointF A = new PointF(e.X, e.Y);pomeraj = newbool[n];for (int i = 0; i < n; i++)pomeraj[i] = o[i].SadrziTacku(A);}

    private void picture Box1 MouseUp(object sender, MouseEventArgs e){

  • 38 S. Matkovi, M. urixi

    x = y = -1;}

    private void picture Box1 MouseMove(object sender, MouseEventArgs e){if (x != -1 && y != -1)

    {for (int i = 0; i < n; i++)if (pomeraj[i]) o[i].Pomeri(e.X - x, e.Y - y);x = e.X;y = e.Y;pictureBox1.Refresh();}

    }

    Primer 3. Funkcija.Posmatrajmo matematiqke funkcije, definisane na skupu realnih brojeva.

    Najprostije realne funkcije su konstante (funkcije oblika f(x) = c, c R) ipromenive (f(x) = x). Sve ostale gradimo primenom osnovnih aritmetiqkihoperacija ili specijalnih funkcija (trigonometrijske, logaritamske, eksponen-cijalne . . . ) na prethodno izgraene funkcije.

    Generalizacijom moemo doi do osnovne klase Funkcija. Za svaku funk-ciju moemo odrediti vrednost u zadatoj realnoj taqki i nacrtati grafik u od-reenom intervalu. Odreivae vrednosti se razlikuje od funkcije do funkcijepa metod Vrednost(double x) mora biti apstraktan kao i sama klasa. Postu-pak crtaa grafika je za sve funkcije isti (spajamo taqke sa koordinatama (x,Vrednost(x)) za uzastopne vrednosti x) pa ga realizujemo u klasi Funkcija(metod Nacrtaj). U osnovnoj klasi moemo realizovati i operatore za osnovnearitmetiqke operacije jer se izvrxavaju na isti naqin, bez obzira na to kojefunkcije se primeuju.

    Iz klase Funkcija, specijalizacijom, izvodimo klase Konstanta, Promen-ljiva, SlozenaFunkcija, Sinusna . . . U svakoj od ovih klasa mora se prede-finisati apstraktni metod Vrednost. Klase SlozenaFunkcija i Sinusna zaatribute imaju druge funkcije xto je u skladu sa odgovarajuim matematiqkimfunkcijama (znamo da je parametar sinusne funkcije proizvona realna funkci-ja a sloena funkcija predstava rezultat primene aritmetiqkih operacija naproizvone realne funkcije).abstract public class Funkcija{

    abstract public double Vrednost(double x);public void Nacrtaj(Graphics g, PointF centar, double x0, double x1, float k)

    //centar - (0,0), (x0,x1) - interval, k broj pt u jedinici Dekartovog KS{for (doublex = x0; x

  • Mala xkola objektno orijentisanog programiraa 39

    {return new SlozenaFunkcija(A, B, -);}

    public static Funkcija operator *(Funkcija A, Funkcija B){return new SlozenaFunkcija(A, B, *);}

    public static Funkcija operator /(Funkcija A, Funkcija B){return new SlozenaFunkcija(A, B, /);}

    public static Funkcij aoperator (Funkcija A, Funkcija B){return new SlozenaFunkcija(A, B, );}

    }public class Konstanta : Funkcija

    {double c;public Konstanta(double c1){c = c1;}

    public override double Vrednost(double x){return c;}

    public override string ToString(){return c.ToString();}}

    public class Promenljiva : Funkcija{public override double Vrednost(double x){return x;}

    public override string ToString(){return"x";}}

    public class Sinusna : Funkcija{Funkcija l;public Sinusna(Funkcija f){l = f;}

    public override double Vrednost(double x){returnMath.Sin(l.Vrednost(x));}

    public override string ToString(){return"sin("+l.ToString()+")";}

  • 40 S. Matkovi, M. urixi

    }

    public class SlozenaFunkcija : Funkcija{Funkcija A;Funkcija B;Char operacija;public SlozenaFunkcija(Funkcija a, Funkcija b, Char c)

    {A = a;B = b;operacija = c;}

    public override double Vrednost(double x){switch (operacija){case+: return A.Vrednost(x) + B.Vrednost(x);case-: return A.Vrednost(x) - B.Vrednost(x);case*: return A.Vrednost(x) * B.Vrednost(x);case/: return A.Vrednost(x) / B.Vrednost(x);case: returnMath.Pow(A.Vrednost(x), B.Vrednost(x));}return 0;}

    public override string ToString(){return A.ToString() + operacija + B.ToString();}}

    Sliqno klasi Sinusna moemo definisati i mnoge druge klase koje pred-stavaju realne funkcije qije je izraqunavae realizovano u sistemskoj klasiMath (trigonometrijske, eksponencijalne, logaritamske, . . . ).

    Navodimo i primer jednostavne aplikacije koja crta grafik funkcije f(x) =sin(x2 + 2) 2 na intervalu od 10 do 10.private void btNacrtaj Click(object sender, EventArgs e)

    {Graphics g=pictureBox1.CreateGraphics();Funkcija g1 = new Promenljiva(); //kreiranje promenljive xFunkcija g2 = new Konstanta(2); //kreiranje konstante 2Funkcija g3 = (g1 g2) + g2; //kreiranje funkcije x2+2

    Funkcija f = (newSinusna(g3)) * g2;// kreiranje funkcije sin(x2+2)*2f.Nacrtaj(g, new PointF(pictureBox1.Width/2, pictureBox1.Height/2),-10,10,30);Text = f.ToString();

    }

    Ovo je samo prikaz osnovne ideje o klasama pomou kojih moemo predstavi-ti realne funkcije. Realizacijom konstruktora koji za parametar imaju stringmoemo znaqajno poboxati mogunosti ovog sistema klasa. Sliqno metodu Vre-dnost moemo realizovati metod Izvod koji bi vratio funkciju koja predstavaprvi izvod polazne funkcije. Ostavamo qitaocima da sami usavrxe ovaj sof-tver u skladu sa svojim eama!

  • Mala xkola objektno orijentisanog programiraa 41

    Zakuqak

    Nasleivae nam daje mogunost korixea ve definisane klase za iz-radu novih klasa koje unapred dobijaju veliki deo funkcionalnosti, a imamo imogunost prilagoavaa izvedene klase svojim potrebama. Na taj naqin obez-beujemo vixestruku upotrebu koda (isti kod koristimo u osnovnoj i izvedenojklasi). Zahvaujui tome, programirae je u prethodnom periodu ostvariloznaqajan napredak, jer su programeri usredsreeni na rexavae specifiqnihproblema a veliki deo projekta, pre svega dizajn i strukturu, nasleuju iz kla-sa grupisanih u sistemske biblioteke ili biblioteka drugih programera.

    I u nastavi programiraa nasleivae se moe vrlo lepo iskoristiti. Mo-gue je postupno nadograivati odreene projekte kroz izvoee sve sloenijihklasa. Takoe, profesor moe kreirati osnovnu klasu a acima prepustiti darealizuju po grupama razne izvedene klase da bi na kraju zajedno kreirali vrloupotrebive aplikacije.

    Ovim zavrxavamo ,,Malu xkolu OOP u C# na stranicama vaxeg qasopisa.Nadamo se da smo vas bar malo zainteresovali i da smo vam pomogli da ovesavremene metode programiraa pribliite svojim acima.

    Matematiqka gimnazija, Kraice Natalije 37, Beograd

    1234