User Tools

Site Tools


codeq:vivid2015

Članek za eno najprestižnejših konferenc na območju osrednje Slovenije. Navodila za oblikovanje članka.

Uvod

  • motivacija - bluzenje iz projekta

Pregled aplikacije

Letos smo na vajah pri predmetu Principi programskih jezikov uporabljali prototipno različico spletne aplikacije za poučevanje prologa. V tem razdelku bomo opisalo splošno delovanje aplikacije, v nadaljevanju pa se bomo posvetili podrobnejšemu pregledu izbranih komponent. Slika 1 prikazuje uporabniški vmesnik aplikacije.

Slika 1: (levo) izbira naloge, (desno) urejevalnik.

Kot večina računalniških sistemov za poučevanje tudi naša aplikacija temelji na reševanju problemov. Glavni meni (slika 1a) tako vsebuje seznam nalog, ki so na voljo za reševanje. Za vsakega uporabnika sistem vodi evidenco nalog, ki jih je rešil delno ali v celoti; v seznamu je to označeno z sivo oziroma zeleno piko pred imenom naloge. Prav tako je prikazan delež nalog, ki jih je uporabnik rešil v posamezni kategoriji.

Slika 1 (desno) prikazuje vmesnik za reševanje nalog. Naloga na sliki zahteva definicijo relacije “X je sestra od Y” z uporabo podatkov o starševstvu in spolu. Družinsko drevo, ki predstavlja te podatke, je na sliki 2 (levo). Na isti sliki (desno) je tudi grafični prikaz zahtevane relacije sister(X,Y).

Slika 2: (levo) primer družinskega drevesa, (desno) grafični prikaz relacije sister(X,Y).

Uporabnikova rešitev na sliki 1 je skoraj pravilna, manjka le še pogoj, da X in Y nista ista oseba (brez tega pogoja bo prolog namreč sklepal, da je vsaka ženska sestra sama sebi). Ista slika vsebuje tudi primere različnih tipov povratnih informacij, ki jih generira naš sistem; podrobneje jih bomo razložili v naslednjih razdelkih.

Trenutna različica spletne aplikacije je dokaj osnovna, a vsebuje vse poglavitne komponente, ki jih imajo podobni sistemi:

  1. razlago naloge in primere;
  2. urejevalnik programske kode, kamor uporabnik piše svojo rešitev;
  3. možnost izvajanja poljubnih poizvedb;
  4. testiranje pravilnosti programov s pomočjo testnih primerov in
  5. možnost takojšnjih individualiziranih povratnih informacij.

Poleg tega ima uporabnik možnost vpogleda v že rešene programe, ki jih lahko uporablja pri pisanju novih rešitev.

Ob koncu semestra smo opravili neformalno anketo, s katero smo želeli oceniti zadovoljstvo študentov z aplikacijo. Odzivi študentov so bili pretežno pozitivni, predlagali pa so tudi vrsto možnih izboljšav. Mnenja iz ankete bomo podrobneje predstavili v sledečih razdelkih; tukaj navajamo le nekaj splošnih vtisov, ki izpostavljajo prednosti takega pristopa k vajam:

Overall dobra aplikacija. Všeč mi je to, da mi ni bilo potrebno doma nastavljati določenih stvari, nalagati knjižnice, etc ampka je bilo vse na voljo na internetu.
Aplikacija je v splošnem super, saj se z njo dosti lažje učiš kot pa če bi moral programirati in preverjati pravilnost svoje rešitve v programu, kjer tudi nimaš na voljo avtomatskega preverjanja pravilnosti rešitve tako kot ste si jo zamislili.

Izbrane funkcije

Testni primeri

Najosnovnejša funkcija sistemov za poučevanje je možnost preverjanja rešitev. Pred uvedbo spletne aplikacije so študenti na vsakih vajah poleg novih nalog dobili še “uradne” rešitve za naloge prejšnjega tedna, s katerimi so lahko preverili svoje rešitve. Tak pristop ima dve očitni slabosti: študent lahko nalogo reši na drugačen način, zaradi česar je rešitvi težko primerjati; poleg tega pa lahko med reševanjem naloge in povratno informacijo mine precej časa.

Ker je v splošnem nemogoče samodejno preveriti, ali dan program pravilno opravlja neko funkcijo, sistemi za poučevanje programiranja ponavadi za preverjanje rešitev uporabljajo testne primere. Učitelj za vsako nalogo določi množico testnih vhodov, sistem pa preveri odgovore, ki jih uporabnikov program vrne pri teh vhodih. Dan program sprejmemo kot pravilno rešitev takrat, ko pravilno reši vse testne primere. Na ta način pokrijemo vse možne rešitve, ki se lahko konceptualno precej razlikujejo. Primer testnega vhoda za nalogo sister/2 iz prejšnjega razdelka je vprašanje

?- sister(vanessa,vanessa).

Pravilen program odgovori “false”, medtem ko napačen program iz slike 1b odgovori “true”. Glede na kombinacijo pravilno in narobe rešenih testnih primerov lahko sklepamo o prisotnosti določenih konceptualnih napak v programu. V zgornjem primeru lahko tako z veliko gotovostjo sklepamo, da v rešitvi manjka pogoj, da X in Y nista ista oseba.

Kljub široki uporabi imajo testni primeri nekaj pomanjkljivosti. Prva je ta, da ne zagotavljajo, da je nek program pravilna rešitev dane naloge, temveč le, da uspešno prestane vse teste. Ta problem rešujemo s premišljeno izbiro testnih primerov, ki jih v primeru napak tudi posodabljamo.

Drug problem je ta, da morajo za uspešno preverjanje vsaj nekateri testni primeri ostati skriti. V nasprotnem primeru bi uporabnik lahko spisal program, ki vrne pravilni odgovor samo za dane vhode, sistem pa bi ga sprejel kot pravilno rešitev naloge. Po drugi strani pa skriti testni primeri lahko predstavljajo problem:

Ni izpisa testnih primerov. Se je zgodilo, da sam nisem mogel najti protiprimera s katerim bi našel napako v programu, testiranje pa ni bilo 100%.

Naključni protiprimeri

Ta problem smo rešili tako, da smo v sistem dodali funkcijo za generiranje naključnih testnih primerov. Kadar uporabnik pošlje nepravilen program v testiranje, mu sistem poleg števila opravljenih testov izpiše še protiprimer, za katerega uporabnikov program vrne nepravilni odgovor.

Delovanje te funkcije si oglejmo na primeru predikata gcd(A,B,D), ki poišče največji skupni delitelj D števil A in B. Za vsako nalogo definiramo vzorec, na podlagi katerega sistem generira naključne kombinacije vhodnih podatkov; za predikat gcd(A,B,D) je ta vzorec

[int(1,100),int(1,100),out].

To pomeni, da sta prva dva argumenta celi števili med 1 in 100, zadnji argument pa predstavlja izhod programa - v tem primeru največji skupni delitelj izbranih števil. Ko uporabnik pošlje nepravilen program v testiranje, sistem najprej zgenerira nov nabor vhodnih podatkov (v tem primeru dve števili). Na tem vhodu požene pravilno rešitev in uporabnikov program. Če sta rezultata enaka, postopek ponovi, v nasprotnem primeru pa vrne generiran vhod kot protiprimer, na katerem uporabnikov program ne deluje pravilno.

To funkcionalnost smo kot manjši dodatek implementirali šele po začetku semestra, a se je hitro izkazala za eno najuporabnejših orodij v našem sistemu. Protiprimei so v veliko pomoč študentu pri iskanju napak v programu, saj lahko na njih simulira izvajanje programa in tako hitreje odkrije mesto napake.

Iz tehničnih razlogov smo naključne protiprimere zaenkrat implementirali le za določene naloge. Na njihovo uporabnost najbolje kažejo izjave študentov, ki so jih pri drugih nalogah pogrešali:

Izpis protiprimera v VSEH primerih bi bil odličen.
Glavni problem je bil to, da pri veliko nalogah ne izpiše protiprimerov, kar bi zelo olajšalo lovljenje hroščev.

Samodejno odpravljanje napak

Prednost računalniških sistemov za poučevanje je tudi v tem, da nam omogočajo zajemanje podatkov o različnih postopkih reševanja. Naš sistem za vsak poskus hrani podrobno sled uporabnikove aktivnosti. Ta sled vključuje vse spremembe programske kode – vstavljanje oziroma brisanje znakov – in ostale interakcije s spletno aplikacijo, kot je izvajanje poizvedb in testiranje rešitve.

Te podatke uporablja metoda za samodejno odpravljanje napak, ki jo razvijamo v našem laboratoriju~\cite{lazar2014data}. Osnovna ideja je, da na nepravilnem programu preizkušamo popravke, ki so jih pri reševanju iste naloge naredili prejšnji uporabniki. Cilj je najti zaporedje popravkov, ki napačen program pretvori v pravilnega (glede na testne primere).

Naša metoda deluje na nivoju besedila in je zato skoraj popolnoma neodvisna od programskega jezika. Za vsako obstoječo rešitev razdeli zaporedje vstavljenih in izbrisanih znakov na zaporedje t.i. vrstičnih popravkov. Popravek je urejen par (prej,potem), ki predstavlja transformacijo ene vrstice v programu. Poleg začetnega in končnega stanja ima vsak popravek tudi pripadajočo verjetnost – delež uporabnikov, pri katerih se je v programu pojavila vrstica prej in so jo spremenili v potem. Nekaj primerov pogostih popravkov za predikat sister(X,Y) je v tabeli 1.

Prej Potem Verjetnost
female(Y) female(X) 0.77
parent(Y,X) parent(X,Y) 0.62
mother(X,Y) parent(X,Y) 0.71
/ X \== Y 0.82

Tabela 1: tipični popravki za predikat sister(X,Y).

Prva dva primera popravita napačne argumente v podciljih; tretji primer zamenja podcilj mother(X,Y) s pravilnim predikatom parent(X,Y); zadnji pa vstavi novo vrstico, ki pravi, da X in Y ne smeta biti ista oseba – to je tudi popravek, ki ga predlaga aplikacija na sliki 1b.

Ko dobi nepravilni program, ga naša metoda poskusi popraviti z različnimi zaporedji popravkov. Pri tem najprej preizkusi krajša zaporedja bolj pogostih popravkov. S tem želimo doseči, da bo končni program čim bolj podoben začetnemu oziroma da bodo posamezni popravki uporabniku lažje razumljivi. Če najdemo ustrezno zaporedje popravkov, ga uporabniku seveda ne smemo razkriti, saj bi mu s tem povedali rešitev naloge. Namesto tega v nepravilnem programu le označimo mesta, kjer so potrebne spremembe.

Ker je metoda še v razvoju in še nismo zbrali dovolj velike množice rešitev, so rezultati mešani. V nekaterih primerih, sploh pri lažjih nalogah, hitro odkrije ustrezno rešitev. Pri kompleksnejših nalogah začne pristop na nivoju besedila kazati pomanjkljivosti, zato bomo v prihodnosti metodi dodali tudi elemente sintaktične analize programa. Prav tako bomo izboljšali predstavitev namigov uporabniku z bolj specifičnimi sporočili.

Vnaprej pripravljeni namigi

Samodejna analiza programske kode nam lahko pomaga pri podajanju povratnih informacij, vendar ima svoje omejitve. Lahko sicer odkrije, kaj je potrebno popraviti v programu, a je take popravke težko preslikati v višjenivojske koncepte. Več študentov je izrazilo željo po bolj specifičnih namigih:

Izboljšal bi način, kako namigi prepoznajo kje se program zmoti oz. da bi bili ti morda za začetnika lažje razumljivi.
Do določene mere bi razkril na kak način bi mogel določen program delovat, naprej pa bi sam študent dopolnil.

Takih namigov letos nismo implementirali; aplikacijo smo uporabljali na vajah, kjer je bil za pojasnila zmeraj na voljo asistent. V okviru projekta želimo aplikacijo prirediti tudi za samostojno učenje. Vsaki nalogi bomo zato dodali še podrobnejše razlage z grafičnimi pojasnili. Na sliki 2b je primer grafičnega prikaza relacije sister(X,Y).

Ročno pripravljeni namigi bodo služili tudi za razlago pogostih napak. Tukaj si oglejmo primer takega namiga za nalogo sins/3 (“sorted insert”). Gre za nalogo, kjer mora študent definirati predikat za vstavljanje novega elementa v urejen seznam števil. V prologu lahko neposredno dostopamo le do prvega elementa v seznamu, zato moramo pregledovati seznam od leve proti desni, dokler ne najdemo obstoječega elementa H, ki je večji od novega elementa E. Na tem mestu vstavimo nov element E pred H, a študenti velikokrat zamenjajo njun vrstni red. To napako se da odkriti z ustreznimi testnimi primeri, zato lahko vnaprej pripravimo ustrezno razlago; primer diagrama za to situacijo je na sliki 3.

Slika 3: primer namiga za predikat sins/3.

Poigritev

Nazadnje omenimo še en vidik aplikacije, ki ga nismo načrtovali, a se je hitro izkazal za bistveno prednost pred obstoječim načinom dela na vajah. Gre za t.i. “poigritev” (angl. gamification) oziroma uporabo prijemov iz računalniških iger, ki so primarno namenjeni motivaciji in ohranjanju zanimanja za uporabo aplikacije. Tipičen primer poigritve je podeljevanje značk (angl. badges) uporabnikom za razne dosežke. Značke delujejo kot zunanji motivacijski faktor, s katerim skrajšamo čas med vloženim delom in nagrado – tudi če je to le ikona na zaslonu.

Naš sistem ne vsebuje nobenih funkcionalnosti, ki bi bile primarno namenjene poigritvi. Kljub temu pa se je izkazalo, da že uvodni zaslon s seznamom nalog (slika 1a) opravlja podobno funkcijo. Študent namreč vidi, koliko nalog je na voljo v vsakem poglavju in koliko jih je že rešil. Vsaka rešena naloga to statistiko malo izboljša – zelena pika dobi vlogo značke – in s tem takoj nagradi študentov trud. Opazili smo tudi, da študenti pri problemih vztrajajo dlje časa, da bi dosegli 100% rešenih nalog za posamezni sklop. Razlogi za to so verjetno sorodni razlogom za priljubljenost raznih zbirateljskih dejavnosti in iger.

V naslednji različici aplikacije bomo eksplicitno podprli poigritev z značkami – recimo za pravilno rešitev v prvem poskusu ali v zelo kratkem času. Uporabnik bo na posebnem zaslonu lahko pregledoval dobljene značke in splošno statistiko reševanja.

Diskusija

codeq/vivid2015.txt · Last modified: 2015/07/14 17:15 by timotej