Sunteți pe pagina 1din 6

03.12.

2013

Tema 2 - Fun with bullets [Programare Orientat pe Obiecte]

Programare Orientat pe Obiecte

Tema 2 - Fun with bullets


Deadline: 03.12.2013 Responsabili: Cristina Ciocan, Paul Urziceanu Data publicarii: 17.11.2013 Data ultimei modificari: 26.11.2013 11:02 24.11.2013 Am adaugat un punctaj-bonus pe care il gasiti detaliat la sectiunea Punctaj 15:18 23.11.2013 Am modificat checker-ul sa ignore liniile goale. 19:54 18.11.2013 Am modificat DrawManager.java in scheletul de cod. Am updatat sa fie aceeasi versiune de checker la sectiunea de resurse ca si pe vmchecker. 16:50 18.11.2013 Am modificat sectiunea cu dilatarea obiectelor si coeficientul pe care trebuie sa-l folositi in tema este 10 dref(d) = -d/10 - id 21:34 26.11.2013 Amanare deadline pana pe 03.12.2013 cs.curs picat In cazul in care aveti intrebari si nu este forumul functional, ne puteti trimite intrebarile pe e-mail si va vom raspunde cat de repede putem: cristina.mihaela.ciocan@gmail.com paul.urziceanu@gmail.com

Obiective
utilizarea corecta a mostenirii si agregarii de clase organizarea eficienta a claselor in pachete incapsularea datelor si utilizarea modificatorilor de acces utilizarea claselor abstracte si/sau a interfetelor

Descrierea problemei
Introducere
Newton, Pitagora si Lagrange organizeaza pentru voi, studentii din anul 2 de la Facultatea de Calculatoare, un turneu de tras cu arma. Insa, pentru a fi totul mai interesant fiecare din cei trei au complicat jocul astfel: Pitagora a pus la dispozitie mai multe tipuri de proiectile cu forme geometrice diverse alcatuite din diferite materiale. Newton a descris miscarea si traiectoria proiectilelor cu atmosfera si modul in care acestea se corodeaza in contactul cu atmosfera. Lagrange a calculat pentru fiecare tip de proiectil cum ar arata conturul produs prin ciocnirea tintei. Pe scurt, un student are la dispozitie mai multe proiectile pe care le va lansa la diferite momente de timp si de la o anumita distanta catre o suprafata tinta. Cerinta problemei este sa calculati cum va arata aceasta suprafata (numita si ecran in enuntul temei) in urma impactului cu multiplele proiectile lansate.

Tipuri de proiectile
Pitagora, pasionat de geometrie, a propus urmatoarele tipuri de proiectile, fiecare avand o forma specifica la coliziunea cu suprafata tinta: id 1 2 3 4 5 6 7 8 Tip proiectil TriGrapeShot Carcass CanisterShot ChainShot Shrapnel HeatedShot SpiderShot SimpleShell Forma geometrica triunghi patrat dreptunghi triunghi patrat romb dreptunghi punct

Studentul are voie sa traga cu orice proiectil din tabelul de mai sus.

Coroziunea atmosferica
Turneul are loc pe o planeta in care atmosfera este diferita fata de cea de pe Pamant si aceasta corodeaza proiectilele astfel incat dupa o anumita distanta acestea se transforma in alt tip de proiectil. Distanta este dictata de urmatoarea formula dependenta de ora, minutul si secunda in care se face tragerea, precum si id-ul asociat fiecarui proiectil:
d 2+( i d*i d*o r a+i d*m i n u t u l+s e c u n d a )%4 2 i d=4

Singurul tip de proiectil care nu se modifica, indiferent de distanta parcursa, este SimpleShell:
d i n f 8=+

elf.cs.pub.ro/poo/teme/tema2

1/7

03.12.2013

Tema 2 - Fun with bullets [Programare Orientat pe Obiecte]

Newton ne ajuta in acest sens si ne explica care este relatia de rudenie intre tipurile de proiectile: TriGrapeShot dupa d1 metri se corodeaza si devine un Shrapnel. Carcass dupa d2 metri se corodeaza si devine un HeatedShot. CanisterShot dupa d3 metri se corodeaza si devine un HeatedShot. ChainShot dupa d4 metri se corodeaza si devine un Shrapnel. Shrapnel dupa d5 metri se corodeaza si devine un SpiderShot. HeatedShot dupa d6 metri se corodeaza si devine un SpiderShot. SpiderShot dupa d7 metri devine un SimpleShell. Exemplu: Presupunem ca lansam un CanisterShot la ora 00:01:00 si suprafata noastra este la distanta ds. Urmarim urmatorii pasi: Vedem in ce se poate transforma CanisterShot: CanisterShot HeatedShot HeatedShot SpiderShot SpiderShot SimpleShell Calculam pentru fiecare posibila transformare distanta necesara corodarii proiectilului: d3 = 42 + (3 * 3 * 0 + 3 * 1 + 0) = 45 d6 = 48 d7 = 49 d8 = +inf Vom obtine urmatoarele cazuri pentru proiectilul nostru initial: daca ds < d3 atunci, la impactul cu suprafata, proiectilul va fi devenit CanisterShot, ca atare forma impregnata pe ecran va fi cea corespunzatoare unui CanisterShot (dreptunghi). daca ds > d3, dar ds - d3 < d6 atunci, la impactul cu suprafata, proiectilul va fi devenit HeatedShot, iar forma impregnata va fi un romb daca ds - d3 > d6, dar ds - d3 - d6 < d7 atunci, la impactul cu suprafata, proiectilul va fi devenit SpiderShot, iar forma impregnata va fi un dreptunghi in final, daca ds - d3 - d6 - d7 > 0 , atunci SpiderShot se corodeaza si va deveni un SimpleShell care nu se va mai coroda indiferent cat de mare este ds si pe ecran se va observa un punct.

Traiectoriile caracteristice fiecarui proiectil


Studentul trage de la o anumita distanta d, la un anumit moment de timp t, cu un proiectil, la o anumita pozitie (px , py), pe o tinta dreptunghiulara pe care o vom numi ecran; ecranul are o lungime si o latime caracteristice. Consideram ca ecranul are dimensiunile ex , ey, iar coordonata (0,0) se afla in coltul din stanga sus al dreptunghiului.

Cand un proiectil loveste ecranul, Newton ne spune ca acesta va lasa forma descrisa de Pitagora pentru fiecare dintre figuri. Asadar, fiecare proiectil are un centru de greutate Cg care, ulterior proiectiei pe ecran, va fi chiar centrul de greutate al figurii 2D reprezentative. Daca studentul trage cu proiectilul la pozitia P = {x,y} atunci inseamna ca, daca ar ajunge nedeviat(vezi sectiunea urmatoare), centrul de greutate al figurii de pe ecran ar fi Cg = P = {x,y} . Newton insa are cateva observatii de facut cu privire la traiectoriile proiectilelor. In functie de distanta dist parcursa, fiecare dintre proiectilele avand o forma aerodinamica mai ciudata, isi modifica anumite coordonate conform urmatoarelor formule. Definim dx (dist ) si dy(dist ) ca fiind deplasarea centrului de greutatea al proiectilului fata de pozitia initiala. xf(dist ) este pozitia finala pe Ox in functie de distanta parcursa yf(dist ) este pozitia finala pe Oy in functie de distanta parcursa
x x ( d i s t )=x ( d i s t ) i+d f y y ( d i s t )=y ( d i s t ) i+d f

(toate distantele se masoara in metri)

elf.cs.pub.ro/poo/teme/tema2

2/7

03.12.2013

Tema 2 - Fun with bullets [Programare Orientat pe Obiecte]

Pentru fiecare proiectil, Newton ne spune modificarile aferente fiecarei axe: Tip proiectil TriGrapeShot Carcass CanisterShot ChainShot Shrapnel HeatedShot SpiderShot SimpleShell dx dist 0 -dist 0 round(sin(dist * PI / 2)) 0 round(sin(dist * PI / 2)) 0 dy 0 dist 0 -dist 0 round(cos(dist * PI / 2)) round(cos(dist * PI / 2)) 0

Exemplu: Presupunem ca lansam un Carcass la pozitia P = {70,70} pe ecran si la o distanta de 30 de metri fata de acesta. Distanta la care se corodeaza intr-un HeatedShot este de 65 de metri, insemnand ca acesta atinge ecranul fara sa se transforme in alt tip de proiectil. Insa, centrul de greutate al figurii proiectate pe ecran nu va fi la C 7 0 , 7 0 } , g={ ci din cauza faptului ca a parcurs 30 de metri, va fi decalat cu d i s t=3 0 , x = 0si d y=d deci rezulta Cg = {70,100}. Putem observa ca un SimpleShell trece nedeviat oricat de multa distanta ar parcurge.

Proiectarea obiectelor pe ecran


Pana in acest moment, stim ca tragem cu un proiectil de la o distanta dfata de ecran la o anumita pozitie p , cunoastem modul in care se corodeaza si implicit cum se transforma fiecare tip de proiectil si stim de asemenea si traiectoria sa in aer, dar trebuie sa vedem cum ajungem sa proiectam figura pe ecran pornind de la pozitia centrului de greutate. Lagrange vine in ajutor si ne spune ca daca stim care este pozitia centrului de greutate vom putea sa proiectam fiecare figura geometrica (patrat, triunghi, dreptunghi, romb). Pentru simplitate, Lagrange defineste o marime de referinta ref cu ajutorul careia defineste fiecare figura relativ la centrul ei de greutate. Cu alte cuvinte, o figura geometrica este definita pe baza unui centru de greutate, o marime de referinta si o lista de varfuri ale caror coordonate se calculeaza pe baza primelor doua in functie de fiecare figura.

elf.cs.pub.ro/poo/teme/tema2

3/7

03.12.2013

Tema 2 - Fun with bullets [Programare Orientat pe Obiecte]

Exemplu: Presupunem ca a lovit ecranul un proiectil HeatedShot cu C 4 0 , 4 0 }si r e f=1 0 . g={ Forma sa este un romb si are 4 varfuri pe care trebuie sa le determinam. Amintesc ca in stanga sus a ecranului este coordonata {0,0}. Notam varfurile rombului cu v sus,v jos,v stanga,v dreapta.
v 0 ,2*r e f } s u s=C g+{ v 0 ,2*r e f } j o s=C g+{ v r e f,0 } d r e a p t a=C g+{ v r e f ,0 } s t a n g a=C g+{

Afland varfurile, mai trebuie doar sa tragem 4 linii pentru a realiza conturul. In implementarea problemei, veti avea la dispozitie o functie care primeste ca parametru un punct de start, un punct de sfarsit, ecranul pe care sa deseneze si un simbol (descris mai jos), iar aceasta deseneaza o linie intr-o matrice de char-uri ce va reprezenta suprafata voastra. Fiecare figura geometrica are un simbol asociat (aveti aceste simboluri si in scheletul de cod): punct P patrat S romb R dreptunghi D triunghi T iar matricea initiala este formata din caracterul '.', inseamnand pozitie nealterata de impactul cu un proiectil. Daca 2 linii se intersecteaza, pe ecran va trebui sa apara in acel punct, simbolul caracteristic proiectilului care a ajuns ultimul. Atunci cand un proiectil se corodeaza si se transforma in alt proiectil, implicit pentru ecran, figura 1 cu Cg1 si ref 1 va transfera cele doua caracteristici figurii 2.

elf.cs.pub.ro/poo/teme/tema2

4/7

03.12.2013
Asta inseamna ca:
C g 2=C g 1 r e f e f 2=r 1

Tema 2 - Fun with bullets [Programare Orientat pe Obiecte]

Dilatarea dimensiunilor proiectilelor


Lansarea proiectilelor se face cu o viteza si o acceleratie extrem de mari, astfel incat Lagrange observa ca, desi noi avem o dimensiune initiala r e f , pe parcurs dimensiunile se contracta si evident va scadea si marimea de referinta. Coeficientul de scadere este strict dependent de distanta parcursa, cat si de tipul proiectilului. Asadar, matematicianul ne ofera urmatoarea formula: ref i + dref(dist) = ref f(dist) Modificare d ( d )=d / 5-i d(cu valoarea 5 se exemplifica mai jos, in tema veti folosi valoarea 10 dupa formula urmatoare: r e f d ( d )=d / 1 0-i d(d este o valoare de tip int deci 4/5 = 0, 9/5 = 1 etc., iar id-ul este cel definit de Pitagora pentru fiecare tip de proiectil) r e f Se garanteaza ca obiectele sunt destul de mari astfel incat sa nu poata fi micsorate la dimeniuni negative. Exemplu: Lansam un TriGrapeShot cu dimensiunea initiala Stim ca:
r e f=3 0la

o distanta

d i s t=4 3de

metri de ecranul de dimensiuni d i m={ 3 0 0 , 3 0 0 }la pozitia

P={ 5 0 , 5 0 } , la

momentul de timp 1:01:00.

d 2+( i d*i d*o r a+i d*m i n u t u l+s e c u n d a )%4 2 i d=4

TriGrapeShot Shrapnel SpiderShot SimpleShell id-urile corespunzatoare sunt 1 5 7 8

Calculam :
d 2+( i d*i d*o r a+i d*m i n u t u l+s e c u n d a )%4 2 1=4 d 2+( 1+1+0 )%4 2=4 4 1=4

TriGrapeShot este la 43 de m ceea ce inseamna ca va lovi ecranul fara sa se transforme in Shrapnel. Calculam deplasarile pe axele Ox si Oy: dx = dist = 43 dy = 0
C d , d }={ 9 3 , 5 0 } g=P+{ x y

Calculam si modul in care se modifica

r e f :

d ( d i s t )=d i s t / 5-i d=4 3 / 5-1=9 r e f r e f=r e f+d ( d i s t )=3 0-9=2 1 r e f

Calculam varfurile triunghiului:


v 0 ,2*r e f }={ 9 3 ,8 } s u s=C g+{ v r e f ,r e f }={ 1 2 4 , 7 1 } d r e a p t a=C g+{ v r e f ,r e f }={ 7 2 ,7 1 } s u s=C g+{

Apelam metoda de desenarea a liniei:

elf.cs.pub.ro/poo/teme/tema2

5/7

03.12.2013
line(v sus,v dreapta,'T',screen) line(v sus,v stanga,'T',screen) line(v dreapta,v stanga,'T',screen)

Tema 2 - Fun with bullets [Programare Orientat pe Obiecte]

Metoda de desenarea a unei linii tine cont si daca punctele sunt pe langa ecran sau daca linia e partial in ecran, asadar nu va trebui sa tratati cazuri de exceptie in acest sens.

Cerinte
Implementati problema descrisa mai sus pornind de la scheletul de cod pus la dispozitie in resurse. Programul va trebui sa primeasca ca parametru un fisier de intrare fisier si sa scrie matricea calculata intr-un fisier cu numele fisier_out. Fisierul de intrare < n u m e _ f i s i e r >va avea urmatoarea forma: pe prima linie dimensiunile ecranului: 2 numere ex si ey pe a doua linie se va afla un numar Nce va reprezenta numarul de proiectile ce vor fi lansate spre tinta urmeaza Nlinii unde se gasesc pe fiecare linie: tipul_de_proiectil ref hh:mm:ss dist posx posy Fisierul de iesire < n u m e _ f i s i e r > _ o u tva avea ey linii si ex coloane reprezentand matricea asociata ecranului pe care se proiecteaza figurile geometrice.

Implementare
Pentru parsarea unei linii din fisierul de intrare, puteti folosi metoda Pentru operatiile matematice (sin, cos, round), utilizati clasa
M a t hdin s p l i ta

clasei S t r i n gsau puteti utiliza o clasa specializata precum

S t r i n g T o k e n i z e r [2][3].

pachetul u t i l .
B u f f e r e d I n p u t S t r e a m [7]

Citirea din fisier se poate face in mai multe moduri, insa pentru a nu avea probleme utilizati clasa Insa, puteti utiliza orice alta metoda doriti, conditia este sa functioneze corect.

si pentru scriere F i l e W r i t e r [8].

In scheletul de cod, aveti mai multe pachete , fiecare grupand clasele ce fac parte dintr-o anumita arie. Sugestia este sa cititi cu atentie comentariile pentru fiecare clasa si apoi sa incepeti implementarea efectiva a temei. In implementare, trebuie sa folositi conceptul de mostenire corect si eficient intocmai cum reiese din enuntul temei. De asemenea, incercati sa evitati cat mai mult codul copiat, sa utilizati specificatorii de acces, precum si cuvantul cheie final atunci cand este cazul. Pentru orice intrebare legata de scheletul de cod, va rugam sa folositi forumul asociat temei 2. Pentru a testa tema, va punem la dispozitie checker-ul si testele pe care trebuie sa le treaca tema voastra. (vezi sectiunea Resurse[2])

Precizari
Pentru alte intrebari legate de cerinta, implementare, corectare sau punctare va rog intrebati pe forum-ul asociat temei 2.

Corectare
Tema se va corecta folosind platforma vmchecker [7]. Platforma va rula o suita de teste in cadrul carora implementarile temei vor primi la rulare diferite intrari, iar apoi iesirile generate vor fi comparate cu rezultate asteptate. Daca platforma de testare nu acorda niciun punct solutiei, atunci acesta va fi punctajul final al implementarii temei. Neutilizarea mostenirii/agregarii sau a incapsularii intocmai cum sunt sugerate in enunt si in sectiunea de implementare vor duce la acordarea a 0 puncte pe intreaga tema. Toate solutiile vor fi verificate folosind o unealta de detectare a plagiatului. In cazul detectarii unui astfel de caz, atat plagiatorul cat si autorul original vor primi punctaj 0 pe tema si nu li se va permite intrarea in examen!

Punctaj
80p - acordate de vmchecker pentru executia cu succes a suitei de teste 10p - acordate de asistent pe baza calitatii implementarii si a respectarii principiilor POO 10p - acordate de asistent pe baza lizibilitatii codului, a calitatii comentariilor si a fisierului Readme 10p bonus - acordate de catre asistent pe baza implementarii mostenirii descrise in enunt (daca avem lantul de transformari ABC, atunci aceasta sa fie si ierarhia de mostenire din cadrul rezolvarii)

Resurse
UPDATE 7:47 18.11.2013 Am modificat DrawManager pentru a desena cu linii continue. UPDATE 10:36 Modificare pentru a desena in mod unic o linie indiferent care capat este primul dat ca parametru. [1] Schelet UPDATE 15:22 23.11.2013 Am modificat checker-ul sa ignore liniile goale la compararea de output-uri. UPDATE 7:47 18.11.2013 Am modificat checker-ul sa aiba testele corecte pentru testele trigonometrice precum cele de pe vmchecker. [2] Checker Am pus un link doar cu DrawManager.java pe care trebuie sa-l copiati in locul celui vechi. [3] DrawManager.zip

elf.cs.pub.ro/poo/teme/tema2

6/7

S-ar putea să vă placă și