Autorské riešenie
[stiahni imp : py]

  • Počet riešiteľov: 10 / 33 = 30,3 %

  • Úspešnosť riešenia: 3,2 / 6 = 53,3 %

Úlohou je určiť cenu darčeka v dvoch obchodoch po akciových zľavách, ak počiatocná cena v oboch je rovnaká. Podľa zadania poznáme, koľko týždňov pred vianocami sa začína akcia a v ktorom týždni od začiatku akcie chcú korytnačky nakupovať.

Časovú os akcie môžeme nakresliť takto:

alternatívny text k obrázku

Procedúra/funkcia bude mať 3 parametre:

  • pociatocna_cena - počiatočná cena darčeka na začiatku akcie

  • od_zaciatku_akcie - počet týždňov, koľko od začiatku akcie do nákupu uplynulo

  • do_zaciatku_vianoc - počet týždňov od zaciatku akcie do vianoc

Najprv ošetríme prípad, ak vstupné parametre zadáme tak, že čas nákupu je už po vianociach, teda počet týždňov od_zaciatku_akcie > do_zaciatku_vianoc. Po vyhodnotení podmienky testovania vstupných dát program buď pokračuje, alebo vypíše: "Darcek by si kupil az po Vianociach."

Ak podľa vstupných parametrov nákup nastane v akčnom období, potom máme určiť akčnú cenu v dvoch obchodoch, pričom stratégia akcií je v každom iná. Na začiatku je vhodné stanoviť premenné cena1 a cena2, pričom pôvodná počiatocná cena ostáva v premennej  pociatocna_cena.

V obchode KoryDarcek cena1 je znížená každý týždeň o 2%, a kto nakupuje v poslednom týždni dostane ešte aj výpredajovú zľavu 2 Eurá. Ale to len v prípade, ak doteraz znížená cena ešte zároveň nie je menšia ako 2 Eurá.

Môžeme to riešiť pomocou cyklu nasledovne: 

;Imagine logo
opakuj :od_zaciatku_akcie [
  urobtu "cena1 :cena1*0.98
]
ak (zaroven :cena1 > 2 :do_zaciatku_vianoc = :od_zaciatku_akcie)[
  urobTu "cena1 :cena1-2
]

V obchode PrekvapKory je stratégia taká, že každý týždeň počas akcie znižujú cenu o 2 Eurá, pokiaľ cena neklesne pod nulu. Ak nákup je v poslednom týždni, pridajú ešte výpredajovú 2%-nú zľavu zo zvyšnej ceny. Cena2 je vypočítaná akčná cena v tomto obchode: 

;Imagine logo
opakuj :od_zaciatku_akcie [
  ak :cena2 > 2 [
    urobtu "cena2 :cena2-2
  ]
]
ak :do_zaciatku_vianoc = :od_zaciatku_akcie[
  urobTu "cena2 :cena2*0.98
]

Nakoniec ostáva len porovnať ceny v obchode KoryDarček a PrekvapKory a vypísať zistenie.

Riešenie v Imagine môže byť nasledovné:

;Imagine logo
viem VyhodnyNakup :pociatocna_cena :od_zaciatku_akcie :do_zaciatku_vianoc

;pociatocna_cena - pociatocna cena darceka na zaciatku akcie
;od_zaciatku_akcie - pocet uplynulych tyzdnov od zaciatku akcie do nakupu
;do_zaciatku_vianoc - pocet tyzdnov od zaciatku akcie do vianoc


ak2 :od_zaciatku_akcie > :do_zaciatku_vianoc[
  pis [Darcek by si kupil az po Vianociach]
][
  urobtu "cena1 :pociatocna_cena
  urobtu "cena2 :pociatocna_cena
  opakuj :od_zaciatku_akcie [
    urobtu "cena1 :cena1*0.98
  ]
  ak (zaroven :cena1 > 2 :do_zaciatku_vianoc = :od_zaciatku_akcie)[
    urobTu "cena1 :cena1-2
  ]
  opakuj :od_zaciatku_akcie [
    ak :cena2 > 2 [
      urobtu "cena2 :cena2-2
    ]
  ]
  ak :do_zaciatku_vianoc = :od_zaciatku_akcie [
    urobTu "cena2 :cena2*0.98
  ]
  ak2 :cena1 < :cena2 [
    pis [KoryDarcek je vyhodnejsi]
  ][
    ak2 :cena1=:cena2 [
      pis [Obe obchody maju rovnaku zlavu]
    ][
      pis [PrekvapKory je vyhodnejsi]
    ]
  ]
]
koniec

V Pythone vieme využiť efektívnejšie funkcie jazyka, na výpočet cien nepotrebujeme použiť cykly. V prvom obchode Korydarček nie je potrebné používať cyklus na výpočet 2%-nej zľavy po týždňoch, ale je vhodné využiť mocninu:  

#Python
cena1 = pociatocna_cena *0.98**od_zaciatku_akcie

V prípade druhého obchodu PrekvapKory môže nastať prípad, že nie je možné odpočítať z počiatočnej ceny 2 Eurá toľkokrát, koľko je počet týždňov od začiatku akcie, lebo by poklesla cena pod 0. Vtedy odpočítame len toľkokrát, koľkokrát sa dá, celočíselným podielom pociatočnej_ceny a 2 zistíme počet možných odpočtov, a cenu už neznižujeme ďalej.  

#Python
cena2 = pociatocna_cena - min(2*od_zaciatku_akcie, 2*(pociatocna_cena//2))

Ďalší postup je rovnaký ako v prípade riešenia v Logo Imagine.

Možné riešeni v Pythone:

Python
def VyhodnyNakup(pociatocna_cena, od_zaciatku_akcie, do_zaciatku_vianoc):
    ''
    funkcia vypočíta ktorý z dvoch obchodov s rôznou akčnou stratégiou 
    ponúka výhodnejšiu zľavu
    :param pociatocna_cena: je počiatočná cena darčeka na začiatku akcie
    :param od_zaciatku_akcie: je počet uplynulých týždňov od začiatku akcie do nákupu 
    :param do_zaciatku_vianoc: je počet týždňov od zaciatku akcie do vianoc
    :return: vráti vyhodnotenie, ktorá z obchodov ponúka výhodnejšiu akciu
    '''
    if od_zaciatku_akcie > do_zaciatku_vianoc:
         raise ValueError('Darcek by si kupil az po Vianociach.')

    else:
        cena1 = pociatocna_cena *0.98**od_zaciatku_akcie
        if cena1 > 2 and do_zaciatku_vianoc == do_zaciatku_vianoc:
            cena1 = cena1 - 2

        cena2 = pociatocna_cena - min(2*od_zaciatku_akcie, 2*(pociatocna_cena//2))
        if cena2 > 0 and do_zaciatku_vianoc == do_zaciatku_vianoc:
            cena2 = cena2*0.98


        if cena1 > cena2:
            return("PrekvapKory je vyhodnejsí.")
        elif cena1==cena2:
            return("Obe obchody maju rovnaku zlavu.")
        else:
            return("KoryDarček je výhodnejsí.")

print(VyhodnyNakup(5, 10, 10))

Vaše zaujímavé riešenia a najčastejšie chyby

Viacerí ste uvažovali tak, že dobu akcie za ktorú sa určí akčná cena, ste považovali od vianoc, a vtedy koncová výpredajová akcia automaticky sa pridáva stále. Uviedli ste len dve parametre, vstupnú cenu a dobu akcie, čo nie je celkom správne.

Viacerí ste zabudli otestovať prípad, ak cena po zľave v niektorom obchode poklesne pod 0, pričom nie je to možné, aby tovar predávali za zápornú cenu. Pri testovani s vhodnými vstupnými číslami sa to dá odhaliť.

Veľmi ťažko vieme zistiť vaše postupy riešenia, ak pomenujete premenné len s písmenami, napr. a,b,c..., a často to aj vás pomýli pri programovaní, používate ich na nesprávnom mieste, hoci možno dobre ste to mysleli. Používajte radšej skratky, celé slová a vaše riešenia budú prehľadnejšie.

Najkrašie riešenie v Imagine nám poslal tím League_of_Plems, takmer dokonalé riešenie mali BonifacGroup a v Pythone tím Bojovník_Macek.