IT Egzaminai/2022: Skirtumas tarp puslapio versijų
| 223 eilutė: | 223 eilutė: | ||
! Rezultatų failo pavyzdys || Paaiškinimai | ! Rezultatų failo pavyzdys || Paaiškinimai | ||
|- | |- | ||
| | |[[Vaizdas:2023-2-uzd-pvz.png|miniatiūra|313x313px]] | ||
|| | || | ||
* Pratimo pavadinimas; dienų, kai Juozas atliko nurodytą pratimą, skaičius; kiek iš viso laiko minutėmis sugaišta šiam pratimui atlikti. | * Pratimo pavadinimas; dienų, kai Juozas atliko nurodytą pratimą, skaičius; kiek iš viso laiko minutėmis sugaišta šiam pratimui atlikti. | ||
13:51, 23 vasario 2023 versija
1 užduotis. Programavimo konkursas
Į Lietuvos programavimo konkurso finalą pateko penki mokiniai, kurių rezultatai atrankos etape buvo geriausi. Finale mokiniams buvo pateiktos įvairaus sudėtingumo programavimo užduotys. Buvo nurodytas joms atlikti skirtas laiko limitas minutėmis ir jų maksimalus vertinimas taškais. Dalyviai programų failus kėlė į automatinio vertinimo sistemą, kuri tikrino, ar programos teisingos. Kai dalyvio programa pateikdavo teisingus visų testų rezultatus, sistema užfiksuodavo užduoties atlikimo laiką minutėmis. Jei dalyvis išsprendė uždavinį teisingai ir neviršijo tam uždaviniui skirto laiko limito, jis už tą uždavinį gavo maksimalų taškų skaičių; jeigu išsprendė teisingai, bet viršijo laiko limitą, gavo pusę maksimalaus taškų skaičiaus (rezultatas skaičiuojamas sveikaisiais skaičiais; pavyzdžiui, jei maksimalus užduoties vertinimas yra 3 taškai, tai už teisingą užduoties sprendimą, viršijus laiko limitą, dalyvis gavo 1 tašką); jeigu dalyvis uždavinio nesprendė arba išsprendė klaidingai, už jį gavo 0 taškų.
Parašykite programą, kuri rastų didžiausią finale surinktų taškų skaičių ir sudarytų dalyvių, surinkusių daugiausia taškų, sąrašą.
Pradiniai duomenys
Duomenys pateikiami tekstiniame faile U1.txt.
- Pirmoje eilutėje užrašytas finale pateiktų uždavinių skaičius u (1 ≤ u ≤ 12).
- Antroje eilutėje iš eilės nurodytas kiekvienam uždaviniui spręsti skirtas laiko limitas minutėmis. Duomenys atskirti vienu tarpo simboliu.
- Trečioje eilutėje iš eilės nurodytas kiekvieno uždavinio maksimalus vertinimas taškais. Duomenys atskirti vienu tarpo simboliu.
- Tolesnėse eilutėse užrašyti penkių finalo dalyvių duomenys: vardas (10 simbolių) ir kiekvienam uždaviniui spręsti sugaištas laikas minutėmis, užfiksuotas sistemos. Duomenys atskirti vienu tarpo simboliu. Buvo bent vienas dalyvis, kuris teisingai išsprendė bent vieną uždavinį.
Rezultatai
Rezultatus pateikite tekstiniame faile U1rez.txt.
- Pirmoje eilutėje pateikite didžiausią finale surinktų taškų skaičių.
- Tolesnėse eilutėse pateikite dalyvių, surinkusių didžiausią taškų skaičių, sąrašą: dalyvio vardas, jo teisingai išspręstų uždavinių skaičius ir šiems uždaviniams spręsti sugaištas laikas minutėmis. Duomenys atskirti vienu tarpo simboliu. Sąrašas surikiuotas pagal teisingai išspręstų uždavinių skaičių mažėjančiai.
Nurodymai
- Sukurkite ir parašykite vieną funkciją, kuri apskaičiuoja dalyvio surinktų taškų skaičių, teisingai išspręstų uždavinių skaičių ir šiems uždaviniams spręsti sugaištą laiką minutėmis.
| Duomenų failo pavyzdys | Paaiškinimai |
|---|---|
|
6 |
|
| Rezultatų failo pavyzdys | Paaiškinimai |
|
13 |
|
1 užduotis. Sprendimas
# Konstantos
DUOMENŲ_FAILAS = "U1.txt"
REZULTATŲ_FAILAS = "U1rez.txt"
# globalūs kintamieji
# nuskaitysim iš failų
viso_uždavinių = 0
laiko_limitai = []
maks_verinimai = []
# naudosime visoje programoje
dalyviai = {}
maks_taškų = 1
# funkcija skaičiuoti vieno dalyvio rezultatus
# rezultatus prideda prie globalaus kintamojo 'rezultatai'
# parametrai: vardas ir sąrašas
def skaičiuok_balus(vardas, laikai):
# naudosime globalų kintamajį fiksuoti maksimalų surinkta taškų skaičių
global maks_taškų
# kintamieji
išspręsta_uždavinių = 0
surinkta_taškų = 0
viso_trukmė = 0
# kiekvieną uždavinį skaičiuojame atskirai
for i in range(viso_uždavinių):
# konvertuojame kintamuosius iš tekstinės eilutės į skaičius
laikas = int(laikai[i])
limitas = int(laiko_limitai[i])
maks_vertinimas = int(maks_verinimai[i])
# skiriame maks taškų. Vėliau patikriname ar turėtų gauti pusę ar 0 taškų
vertinimas = maks_vertinimas
if laikas > limitas:
vertinimas = maks_vertinimas // 2
if laikas > 0:
išspręsta_uždavinių += 1
surinkta_taškų += vertinimas
viso_trukmė += laikas
if maks_taškų < surinkta_taškų:
maks_taškų = surinkta_taškų
return { 'vardas': vardas, 'uždaviniai': išspręsta_uždavinių, 'balai': surinkta_taškų, 'laikas': viso_trukmė }
# rūšiavimo funkcija
def rūšiuok(rezultatai):
sąrašas = []
# pasiimame tik tuos rezultatus, kurie suringko maks balų
for r in rezultatai:
if r['balai'] == maks_taškų:
sąrašas.append(r)
# rūšiuojame atrinktus rezultatus burbulo principu
while True:
buvo_pakeitimų = False
for i in range(len(sąrašas) - 1):
s1 = sąrašas[i]
s2 = sąrašas[i + 1]
if s1['uždaviniai'] < s2['uždaviniai'] or (s1['uždaviniai'] == s2['uždaviniai'] and s1['laikas'] > s2['laikas']) :
laikinasElementas = sąrašas[i]
sąrašas[i] = sąrašas[i + 1]
sąrašas[i + 1] = laikinasElementas
buvo_pakeitimų = True
if not buvo_pakeitimų:
break
return sąrašas
# spausdiname rezultatus į failą
def atspausdinti(rezultatai):
global maks_taškų
with open(REZULTATŲ_FAILAS, "w") as rašomas_failas:
# pirma eilutė - maksimalus taškų skaičius
rašomas_failas.write(str(maks_taškų))
rašomas_failas.write("\n")
# įrašome pateiktus rezultatus iš eilės
for r in rezultatai:
rašomas_failas.writelines([r['vardas'], " ", str(r['uždaviniai']), " ", str(r['laikas']), "\n"])
# programa
# nuskaitome duomenis iš failo ir priskiriame juos globaliems kintamiesiems
with open(DUOMENŲ_FAILAS, "rt") as skaitomas_failas:
viso_uždavinių = int(skaitomas_failas.readline())
laiko_limitai = skaitomas_failas.readline().split(" ")
maks_verinimai = skaitomas_failas.readline().split(" ")
while True:
tekstas = skaitomas_failas.readline()
if not tekstas:
break
dalyviai[tekstas[:10].strip()] = tekstas[11:].split(" ")
# kiekvieno dalyvio balus apskaičiuojame atskirai pasinaudodami skaičiavimo funkcija
rezultatai = []
for dalyvis in dalyviai:
rezultatai.append(skaičiuok_balus(dalyvis, dalyviai[dalyvis]))
# prafiltruojame ir surūšiuojame rezultatus
galutiniai_rezultatai = rūšiuok(rezultatai)
# atspausdiname
atspausdinti(galutiniai_rezultatai)
2 užduotis. Sportas namuose
Juozas dirba namuose. Norėdamas daugiau judėti, jis nusprendė sausio mėnesį pradėti sportuoti – pagal galimybes atlikti namuose penkis įvairius pratimus. Juozas užrašuose žymėdavosi sportavimo duomenis: kiek kartų sportavo tam tikrą dieną, pratimų pavadinimus, kuriuo dienos metu juos atliko ir kiek laiko minutėmis skyrė nurodytiems pratimams atlikti.
Parašykite programą, kuri apskaičiuotų ir išvestų Juozo sausio mėnesį atliktų pratimų statistiką.
Pradiniai duomenys
Duomenys pateikiami tekstiniame faile U2.txt.
- Pirmoje eilutėje užrašyta, kiek dienų d (1 ≤ d ≤ 31) sausio mėnesį sportavo Juozas.
- Tolesnėse eilutėse užrašyti Juozo sportavimo duomenys: kiek kartų jis sportavo tam tikrą dieną s (1 ≤ s ≤ 7) ir pratimų duomenys: pratimo pavadinimas (14 simbolių), dienos metas (žodis Rytas, Diena, Vakaras; 7 simboliai) ir kiek laiko minutėmis Juozas sugaišo, atlikdamas nurodytą pratimą. Juozas gali tą patį pratimą atlikti tą pačią dieną daugiau negu vieną kartą ir bet kuriuo dienos metu. Duomenys atskirti vienu tarpo simboliu. Buvo bent viena diena, kai Juozas atliko bent vieną pratimą.
Rezultatai
Rezultatus pateikite tekstiniame faile U2rez.txt.
- Įrašykite pratimų pavadinimus, dienų, kai Juozas atliko nurodytus pratimus, skaičių ir kiek iš viso laiko minutėmis sugaišo šiems pratimams atlikti. Pratimų sąrašą surikiuokite abėcėliškai. Duomenis eilutėje atskirkite vienu tarpo simboliu.
- Po kiekvieno pratimo pavadinimo atskirose eilutėse parašykite žodžius Rytas, Diena, Vakaras ir nurodykite, kiek kartų sausio mėnesį Juozas nurodytu dienos metu atliko nurodytą pratimą. Duomenis eilutėje atskirkite vienu tarpo simboliu. Jeigu kurio nors pratimo kuriuo nors dienos metu nebuvo atlikta nė karto, duomenų apie šį dienos metą pateikti nereikia.
Nurodymai
- Programoje naudokite struktūros duomenų tipo masyvą sportavimo duomenims saugoti.
- Sukurkite ir parašykite funkciją, kuri sudarytų pratimų unikalių (nepasikartojančių) pavadinimų sąrašą. Python programavimo kalboje naudokite žodyno duomenų struktūrą arba struktūrą sudarykite, naudodami klases.
2 užduotis. Sprendimas
# Konstantos kurias naudosime programoje
DUOMENŲ_FAILAS = "U2.txt"
REZULTATŲ_FAILAS = "U2rez.txt"
PRATIMO_PAVADINIMO_ILGIS = 14
DIENOS_METO_ILGIS = 7
DIENOS_METAS_RYTAS = "Rytas "
DIENOS_METAS_DIENA = "Diena "
DIENOS_METAS_VAKARAS = "Vakaras"
# Klasė skirta konkretaus pratimo atlikimo duomenims saugoti
# Pratimo pavadimas bus naudojamas kaip raktas žodyne, tad jo saugoti klasėje papildomai nebereikia
class Sportavimas:
def __init__(self):
# Dienų kuriomis buvo atliktas pratimas indekasai
self.dienos = []
# Pratimo atlikimo bendra trukmė
self.trukmė = 0
# Kiek kartų pratimas atliktas konkrečiu dienos metu
self.rytas = 0
self.diena = 0
self.vakaras = 0
# Pridedamas naujas konkretaus pratimo atlikimo įrašas
def pridėk_pratimą (self, diena, trukmė, dienos_metas):
# Jeigu šią dieną pratimo dar nebuvo daryta, tai pažymime dienų sąraše, jog pratimas buvo atliktas
if diena not in self.dienos:
self.dienos.append(diena)
self.trukmė += trukmė
if dienos_metas == DIENOS_METAS_RYTAS:
self.rytas += 1
elif dienos_metas == DIENOS_METAS_DIENA:
self.diena += 1
elif dienos_metas == DIENOS_METAS_VAKARAS:
self.vakaras += 1
# Funkcija dienų skaičiui gauti
def gauk_dienų_skaičių(self):
return len(self.dienos)
# Funcija gražinanti uniklų pratimų sąrašą, kaip reikalaujama egazmino sąlygoje
def gauk_unikalų_pratimų_sąrašą(duomenys):
return list(duomenys.keys());
# Funkcija nuskaitanti faile esančius duomenis
def skaityk_failą():
sportavimas = {}
with open(DUOMENŲ_FAILAS, "r") as skaitomas_failas:
d = int(skaitomas_failas.readline())
for i in range(0,d):
# Nuskaitome s, kartu ir po jo einantį tarpą (1 ≤ s ≤ 7)
s = int(skaitomas_failas.read(2))
for _ in range(0,s):
pratimas = skaitomas_failas.read(PRATIMO_PAVADINIMO_ILGIS)
# Praleidžiame tarpą skiriantį pratimo pavadinimą ir dienos metą
skaitomas_failas.read(1)
dienos_metas = skaitomas_failas.read(DIENOS_METO_ILGIS)
# Praleidžiame tarpą skiriantį pratimo pavadinimą ir dienos metą
skaitomas_failas.read(1)
# Skaitom atlikimo laiką iki aptinkame tarpą
perskaitytas_simobolis = skaitomas_failas.read(1)
trukmė = 0
# Skaitome po simbolį ir "sulipdome" trukmės skaičių
while perskaitytas_simobolis.isdigit():
# Skaitome laiką po simbolį ir verčiame į skaičių
trukmė = trukmė * 10 + int(perskaitytas_simobolis)
perskaitytas_simobolis = skaitomas_failas.read(1)
# Jeigu pratimas sutinkamas pirmą kartą - sukuriame naują `Sportavimas` tipo objektą
if pratimas not in sportavimas:
sportavimas[pratimas] = Sportavimas()
sportavimas[pratimas].pridėk_pratimą(i, trukmė, dienos_metas)
return sportavimas
# Pagalbinė funkcija, skirta dienos meto duomenų įrašymui į failą
def rašyk_dienos_meto_duomenis_į_failą(rašomas_failas, dienos_metas, pratimų_kiekis):
rašomas_failas.write(dienos_metas)
rašomas_failas.write(" ")
rašomas_failas.write(str(pratimų_kiekis))
rašomas_failas.write("\n")
def rašyk_failą(duomenys):
# Pasiimame žodyno raktus kad juos galėtume išrūšiuoti kaip sąrašą
pratimai = gauk_unikalų_pratimų_sąrašą(duomenys)
# Rūšiuojame pavadinimus
pratimai.sort()
with open(REZULTATŲ_FAILAS, "w") as rašomas_failas:
for pratimas in pratimai:
rašomas_failas.write(pratimas)
rašomas_failas.write(" ")
rašomas_failas.write(str(duomenys[pratimas].gauk_dienų_skaičių()))
rašomas_failas.write(" ")
rašomas_failas.write(str(duomenys[pratimas].trukmė))
rašomas_failas.write("\n")
if duomenys[pratimas].rytas > 0:
rašyk_dienos_meto_duomenis_į_failą(rašomas_failas, DIENOS_METAS_RYTAS, duomenys[pratimas].rytas)
if duomenys[pratimas].diena > 0:
rašyk_dienos_meto_duomenis_į_failą(rašomas_failas, DIENOS_METAS_DIENA, duomenys[pratimas].diena)
if duomenys[pratimas].vakaras > 0:
rašyk_dienos_meto_duomenis_į_failą(rašomas_failas, DIENOS_METAS_VAKARAS, duomenys[pratimas].vakaras)
if __name__ == '__main__':
duomenys = skaityk_failą()
rašyk_failą(duomenys)
