PSI/Jun 2022

Izvor: SI Wiki
< ПСИ
Datum izmene: 16. septembar 2023. u 14:57; autor: Etfsibg (razgovor | doprinosi) (→‎Rešenje)
(razl) ← Starija izmena | Trenutna verzija (razl) | Novija izmena → (razl)
Pređi na navigaciju Pređi na pretragu

Junski ispit 2022. godine održan je 10. juna. Trajao je 165 minuta, ukupno je nosio 40 bodova (teorijski deo 12, praktični 28), praktični deo se radio većinom na računaru a teorijski u potpunosti na papiru i radili su se istovremeno. Štampana literatura nije bila dozvoljena, dok je za radne okvire koji su se koristili na praktičnom delu (Django, Laravel, CodeIgniter) bila dostupna dokumentacija. Tekst ispita dostupan je sa stranice predmeta, kao i fajlovi za implementaciju i skript baze.

1. zadatak

Postavka

Razmotrimo sledeći fragment napisan na objektno-orijentisanom pseudojeziku:

public class Button {
    private Lamp itsLamp;
    // other necessary instance variables
    public void poll() {
        if (/* some condition */)
            itsLamp.turnOn();
    }
    // other necessary methods
}
  1. Koji SOLID princip(i) dizajna su prekršeni? Pomoć: klasa Button ne treba da vidi "iznutrice" klase Lamp.
  2. Popraviti i dopuniti dati pseudokod da ne krši SOLID principe i da se pravilno inicijalizuje instance klase Button.

Rešenje

SOLID princip koji je ovde prekršen je Dependency Inversion Principle (DIP), jer klasa Button zavisi od klase Lamp, koja je klasa nižeg nivoa, direktno, umesto preko apstrakcije. Ispravljen kod bi izgledao ovako:

abstract class Button {
    private ILamp itsLamp;
    public void poll() {
        if (/* some condition */)
            itsLamp.turnOn();
    }
    public Button(ILamp itsLamp) {
        this.itsLamp = itsLamp;
    }
}
interface ILamp {
    void turnOn();
}

2. zadatak

Postavka

Želi se implementirati skup celih brojeva (klasa TreeSet) pomoću binarnog stabla pretrage, čiji su čvorovi opisani klasom Node. Dat je nepotpun UML dijagram koji opisuje takvu implementaciju.

Dijagram iz postavke drugog zadatka.
  1. Koja od sledećih ograničenja se mogu izraziti kardinalnostima na dijagramu? Za ona koja mogu zaokružite T i unesite kardinalnost na dijagram, a za ona koja ne mogu zaokružite F.
    1. [T / F] Stablo sastavljeno od Node čvorova je aciklično.
    2. [T / F] A TreeSet može biti prazan skup.
    3. [T / F] Čvor Node ne mora imati dece.
    4. [T / F] Čvor Node može imati jedno dete.
    5. [T / F] Čvor Node može imati najviše dvoje dece.
    6. [T / F] Stablo čvorova Node je uravnoteženo, tako da put od korenog čvora do najudaljenijeg lista nije više nego dvostruko duži od putanje od korenog čvora do najbližeg lista.
    7. [T / F] Čvorovi Node ne dele se među različitim TreeSet skupovima.
    8. [T / F] Ceo broj se može pojaviti u bilo kom TreeSet skupu.
    9. [T / F] Svaki čvor Node ima tačno jedan celobrojni ključ.
    10. [T / F] Podstabla se ne dele u okviru stabla Node čvorova.
    11. [T / F] TreeSet nema više od jednog korenog čvora.
  2. Za klase TreeSet i Node napišite odgovarajuće modele u nekom ORM frejmvorku koji je pominjan na predavanjima i vežbama.

Rešenje

Rešenja stavki prvog zadatka su sledeća:

  1. (F) Stablo sastavljeno od Node čvorova je aciklično. (UML ne može da garantuje da se u objektima ne može naći ciklus)
  2. (T) A TreeSet može biti prazan skup. (Na dijagramu kod root stoji 0-1, dakle može da nema čvora tu)
  3. (T) Čvor Node ne mora imati dece. (Na dijagramu kod children stoji 0-2, dakle može da nema dece tu)
  4. (T) Čvor Node može imati jedno dete. (Na dijagramu kod children stoji 0-2, dakle može da ima jedno dete tu)
  5. (T) Čvor Node može imati najviše dvoje dece. (Na dijagramu kod children stoji 0-2, dakle može da ima dvoje dece tu, ali ne može troje i više)
  6. (F) Stablo čvorova Node je uravnoteženo, tako da put od korenog čvora do najudaljenijeg lista nije više nego dvostruko duži od putanje od korenog čvora do najbližeg lista. (Ovo ne može da se osigura UML kardinalnostima)
  7. (T) Čvorovi Node ne dele se među različitim TreeSet skupovima. (Na dijagramu je na relaciji TreeSetNode dodata kardinalnost na strani stabla)
  8. (T) Ceo broj se može pojaviti u bilo kom TreeSet skupu. (Na dijagramu je na strani Node kod veze sa Integer postavljeno *)
  9. (T) Svaki čvor Node ima tačno jedan celobrojni ključ. (Na strani Integer stoji 1)
  10. (T) Podstabla se ne dele u okviru stabla Node čvorova. (Isti razlog kao pod 7)
  11. (T) TreeSet nema više od jednog korenog čvora. (Na dijagramu kod root stoji 0-1, dakle može da ne više od jednog čvora tu)
Dopunjeni dijagram iz drugog zadatka.

Rešenje druge stavke zadatka je sledeće:

class TreeSet(models.Model):
    root = models.ForeignKey(Node, null=True, on_delete=models.CASCADE)

class Node(models.Model):
    tree = models.ForeignKey(TreeSet, on_delete=models.CASCADE)
    value = models.IntegerField()
    child1 = models.OneToOneField(Node, on_delete=models.CASCADE)
    child2 = models.OneToOneField(Node, on_delete=models.CASCADE)

3. zadatak

Postavka

Posmatra se informacioni sistem za usluge rezervisanja raftinga, smeštaja za rafting i dodatnih aktivnosti. Sistem omogućava prijavu koja zahteva izbor rafting ture, broja noćenja, broja gostiju i opcioni izbor jedne ili više dodatnih aktivnosti.

Svaka rafting tura ima svoj naziv i cenu. Isto važi i za svaku od dodatnih aktivnosti. Cena noćenja zavisi od broja noćenja, tako da su niže cene ako se rezerviše veći broj noćenja. Za svaku od izabranih dodatnih aktivnosti, kao i za rafting koji je obavezno uključen, potreban je po jedan dan boravka, tako da sistem pri prijavi rezervacije, osim provere da li su sva zahtevana polja popunjena, treba da proveri i da li je izabrani broj noćenja odgovarajući. Prijava je validna i ako je izabrani broj noćenja takav da neki dani budu bez aktivnosti ili nije izabrana nijedna dodatna aktivnost. Obavezno polje Nosilac prijave treba da sadrži ime i prezime osobe koja je glavni gost koji rezerviše turu, a broj gostiju (uključujući nosioca) je obavezno polje gde treba upisati numeričku vrednost između 2 i 10.

U slučaju da je forma za prijavu ispravno popunjena, obračunava se i na novoj stranici prikazuje ukupna cena boravka i korisniku daje opcija da potvrdi rezervaciju ili se vrati na stranicu za kreiranje prijave. Ukupna cena se računa na osnovu cene noćenja, rafting ture, uključenih dodatnih aktivnosti i broja gostiju . U slučaju povratka na stranicu za kreiranje prijave, prethodni sadržaj forme za prijavu treba da bude sačuvan. Ako korisnik potvrdi da želi rezervaciju, podaci iz forme za rezervaciju i ukupna cena boravka se čuvaju i prikazuje se početni ekran sa porukom o uspešnoj prijavi.

U slučaju da forma za prijavu nije bila ispravno popunjena, na istoj stranici se prikazuje poruka o grešci, bez brisanja sadržaja forme za prijavu. Poruka treba da kratko i jasno obrazloži kakva je greška napravljena pri popunjavanju prijave (nije popunjeno jedno ili više polja, izabrano više dodatnih aktivnosti nego što je moguće na osnovu broja noćenja itd.).

  1. Realizovati MVC (Model-View-Controller) aplikaciju korišćenjem programskog jezika PHP ili Python. Implementaciju je moguće raditi korišćenjem objektno orijentisanog PHP koda, ili korišćenjem radnih okvira CodeIgniter, Laravel ili Django MTV (Model-Template-View). Aplikacija je potrebno da sadrži isključivo deo sistema koji se odnosi na prijavu rafting ture.
    Očekivani rezultat zadatka 3a): čitav projekat veb aplikacije komprimovati u ZIP arhivu i iskopirati na disk Rad (L:). Isto je potrebno uraditi i ukoliko se radi u radnom okviru.
  2. Korišćenjem alata Selenium IDE, napisati test primere kojim ćete testirati formu za prijavu rafting ture, koja je opisana u tekstu zadatka i implementirana u tački a).
    Očekivani rezultat zadatka 3b): projekat okruženja Selenium IDE, sa svim testovima, snimiti kao fajl sa ekstenzijom .side i prekopirati na disk Rad (L:) . Dovoljno je testove pokrenuti samo u okruženju Google Chrome ili Mozilla Firefox.
  3. Nacrtati dijagram sekvence za funkcionalnost prijave rafting ture, prema opisanoj specifikaciji sistema.
    Očekivani rezultat zadatka 3c): dijagrame nacrtati na ovom papiru.

Rešenje

  • Django i Selenium IDE projekat kao i StarUML dijagram
    • Za pokretanje potrebno je sledeće:
      1. Napraviti rafting bazu
      2. Imati Django instaliran na računaru
      3. U jun2022/settings.py izmeniti kredencijale za bazu sa is1 / tubic na korisnika koji postoji i njegovu lozinku
      4. Zakomentarisati polja rafting_putanja i dodatne_aktivnosti u rafting/forms.py
      5. Pokrenuti python manage.py migrate
      6. Otkomentarisati gorenavedene linije
      7. Pokrenuti python manage.py shell a u njemu pokrenuti:
        from db_init import init
        init()
        exit()
        
      8. Pokrenuti python manage.py runserver
      9. Posetiti http://127.0.0.1:8000
  • CodeIgniter projekat i SQL skripta
    • Za pokretanje potrebno je sledeće:
      1. Pokrenuti SQL skriptu koja će napraviti bazu i popuniti je podacima
      2. U app/Config/Database.php izmeniti kredencijale za bazu sa is1 / tubic na korisnika koji postoji i njegovu lozinku
      3. Imati Composer instaliran
      4. Pokrenuti composer install kako bi se instalirati potrebni paketi za projekat
      5. Pokrenuti php spark serve
      6. Posetiti http://127.0.0.1:8080
Dijagram sekvence tražen u trećoj stavci trećeg zadatka.