1. Johdanto 1.1. Tehtävä Lausekielinen ohjelmointi II -kurssin ensimmäisessä harjoitustyössä on tehtävänä toteuttaa Java-ohjelma, joka laskee merkkijonoa kuvaavia tunnuslukuja. Ohjelma esikäsittelee merkkijonon ennen sen analysointia. Harjoitustyö on ratkaistavissa tähän mennessä opituilla tiedoilla ja ohjelman rakenteen hahmottelun voi aloittaa vaikka saman tien. Tehtävän ratkaisussa ei saa käyttää enemmän ohjelmointia taitavien tuntemia helpompia ohjelmointitekniikoita. Esimerkiksi taulukoiden käyttö on kielletty ja String-luokasta saa käyttää vain muutamaa operaatiota. Kiellon rikkominen johtaa saman tien harjoitustyön hylkäämiseen. Kysy siis harjoitustyönohjaajaltasi, mikäli olet epävarma mitä saa tehdä ja mitä ei. Ohjelman saa halutessaan jakaa operaatioiksi. Tärkein syy ohjelmointitekniikoiden rajoittamiseen on harjoitustyön oppimistavoite, joka on ohjausrakenteiden käyttö laajemmassa mittakaavassa. Jos kaikki on sallittua, niin on todennäköistä, että aloitteleva ohjelmoija tutustuu, esimerkiksi valmiiksi ohjelmointitaitoisen kaverin avulla, myöhemmin opetettaviin menetelmiin pintapuolisesti. Tällöin on vaarana, että ohjelman kirjoittaja ei täysin ymmärrä ratkaisunsa toimintaa eikä tule oppineeksi kuinka valintaja toistorakenteita käytetään. Rajoitusten seurauksena jo ohjelmointitaitoiset kurssilaiset joutuvat käyttämään työhön hieman enemmän aikaa. Tämä on kuitenkin pienempi paha kuin se, että osa ohjelmointia aloittelevista kurssilaisista ei oppisi kunnolla keskeisimpiä taitoja. Harjoitustyö tehdään itse ja lähinnä omalla ajalla. Kaverien kanssa saa keskustella, mutta suora kopiointi eli plagiointi on kiellettyä. Luonnollisesti myös verkosta löytyneen koodin käyttö katsotaan plagioinniksi. Kurssisivuilla julkaistu koodi on vapaasti käytettävissä. 1.2. Pakollisuus ja korvaavuudet Harjoitustyö on pakollinen. Ainoa poikkeus tähän sääntöön ovat harjoitustyön korvanneet opiskelijat. Harjoitustyön voi korvata: 1. Muiden oppilaitosten opinnoilla. 2. Viime vuonna järjestetyn Lausekielinen ohjelmointi II -kurssin hyväksytyllä ensimmäisellä harjoitustyöllä, jos kurssi jäänyt kesken esimerkiksi ase- tai siviilipalveluksen tapaisesta pakottavasta syystä. Kurssin kotisivuilla on annettu tarkempia tietoja osasuorituksista. 3. Edellisten kohtien tapaisella painavalla syyllä. Ensimmäisen kohdan perusteella on annettu kaikki opintokoordinaattorin (Heli Rikala) kurssin vastuuopettajalle (Jorma Laurikkala) esittämät korvaavuudet. Toisen ja kolmannen kohdan osalta on tärkeintä muistaa, että harjoitustyö korvautuu vain, jos opiskelija ottaa yhteyttä kurssin vastuuopettajaan. Tähän mennessä tulleet yhteydenotot ja sopimukset on kirjattu ylös eikä uusia yhteydenottoja näiltä osin tarvita. Lausekielinen ohjelmointi II Syksy 2017 Jorma Laurikkala 1 / 6
2. Merkkijonon esikäsittely ja tunnuslukujen laskeminen Käyttäjän oletetaan antavan aina syötteenä merkkijonon, jossa on vähintään yksi merkki ja korkeintaan 1000 merkkiä. Merkkijono esikäsitellään ennen tunnuslukujen laskua siten, että siitä poistetaan pilkut, pisteet, puolipisteet, kaksoispisteet, kysymysmerkit, huutomerkit, yksinkertaisen lainausmerkit ('), lainausmerkit, jakomerkit (/) ja kaarisulkeet. Lainausmerkki esitetään Javassa kahden merkin yhdistelmänä ('\"'), koska lainausmerkkejä itsessään käytetään merkkijonoliteraalien määrittelyyn. Esikäsittelyn tavoitteena on muokata merkkijonoa siten, että merkkijonon osia erottavat pääosin välilyönnit, jolloin merkkijonon pilkkominen on helpompaa ja osista lasketut tunnusluvut ovat tarkempia. Harjoitustyössä oletetaan, että poistettuja välimerkkejä seuraa yleensä yksi välilyönti. Lisäksi oletetaan, että merkkijonon alussa tai lopussa ei ole välilyöntejä ja että välilyöntejä ei ole peräkkäin. Jos alkuperäinen merkkijono on esimerkiksi "It's a dangerous business, Frodo, going out your door.", poistetaan esikäsittelyssä yksinkertainen lainausmerkki, pilkut ja piste, jolloin tulos on "Its a dangerous business Frodo going out your door". Harjoitustyössä käytetty suoraviivainen esikäsittely saattaa muuttaa luonnollisella kielellä esitetyn merkkijonon merkitystä. Edellisessä esimerkissä suurin sisällöllinen muutos oli supistuman it's muuttuminen possessiivipronominiksi its. Merkkijonon merkityksen muutoksia ei huomioida millään tavalla, jotta harjoitustyö ei kävisi liian vaikeaksi. Ohjelma katkoo esikäsitellyn merkkijonon osiksi välilyöntien kohdilta ja laskee osien lukumäärän, osien pituuksien summan, osien pituuksien keskiarvon kokonaisluvuksi pyöristettynä, lyhimmän osan pituuden, toiseksi lyhimmän osan pituuden, toiseksi pisimmän osan pituuden ja pisimmän osan pituuden. Esikäsitellystä merkkijonosta "Its a dangerous business Frodo going out your door" saadaan yhdeksän osaa: "Its", "a", "dangerous", "business", "Frodo", "going", "out", "your" ja "door", joiden pituuksien 3, 1, 9, 8, 5, 5, 3, 4 ja 4 summa ja keskiarvo ovat 42 ja 4,7 5. Lyhimmän ja toiseksi lyhimmän osan pituudet ovat 1 ja 3. Pisimmän ja toiseksi pisimmän osan pituudet ovat 9 ja 8. Lyhimmän, toiseksi lyhimmän, pisimmän ja toiseksi pisimmän osan pituuksien (min 1, min 2, max 1, max 2 ) päättelyyn liittyy erikoistapauksia. Harjoitustyössä nämä pituudet katsotaan samoiksi, kun osia on yksi tai kaikkien osien pituudet ovat samat. Jos osat ovat esimerkiksi "x" ja "x", niin min 1 = 1, max 1 = 1, min 2 = 1 ja max 2 = 1. Kun osilla on vain kaksi erilaista pituutta, on toiseksi pisimmän osan pituus sama kuin lyhimmän osan pituus ja toiseksi lyhimmän osan pituus sama kuin pisimmän osan pituus. Jos osat ovat esimerkiksi "x" ja "xx", niin min 1 = 1, max 1 = 2, min 2 = 2 ja max 2 = 1. Lyhimpien ja pisimpien osien osalta ei huomioida myöhemmin löydettäviä samanpituisia osia, jolloin lyhin ja toiseksi lyhin pituus samoin kuin pisin ja toiseksi pisin pituus pysyvät erisuurina (min 1 min 2 ja max 1 max 2 ) paitsi, kun kaikki pituudet ovat samoja. Jos osat ovat esimerkiksi "x", "xx", "x" ja "xx", niin min 1 = 1, max 1 = 2, min 2 = 2 ja max 2 = 1, vaikka ensimmäinen ja kolmas osa ja toinen ja neljäs osa ovat samanpituisia. Lausekielinen ohjelmointi II Syksy 2017 Jorma Laurikkala 2 / 6
3. Ohjelman toiminnot Seuraavassa esitellään ohjelman toiminnallisuutta pienten esimerkkien avulla. Laajempia esimerkkiajoja julkaistaan kurssin kotisivujen Opetus Harjoitustyöt Harjoitustyö 1 -kohdassa. Tietojen lukemiseen näppäimistöltä käytetään In-luokan operaatioita. Myös In-luokka löytyy kurssin sivuilta. Huomaa, että harjoitustyössä syötteiden lukuun ei saa käyttää muita keinoja, jotta töiden automaattinen tarkastus (luku 7) onnistuisi varmemmin. Tehtävän helpottamiseksi oletetaan, että ohjelmalle annetaan aina syöte sitä luettaessa ja että ohjelmalle ei tarjota väärän tyyppisiä syötteitä. Kukin syöte kirjoitetaan näppäimistöltä ja annetaan ohjelman käsiteltäväksi Enternäppäintä painamalla. 3.1. Aloitusrivin tulostaminen Käynnistyessään ohjelma tulostaa näytölle tekstin "Hello! I calculate some string statistics." Hello! I calculate some string statistics. Tämä teksti tulostetaan vain kerran. 3.2. Merkkijonon lukeminen Heti aloitusriviä seuraavalle riville tulostetaan "Please, enter a string:". Syötekehotusta seuraavalla rivillä luetaan merkkijono. Ohjelma olettaa, että syötteen pituus on vähintään yksi merkki ja korkeintaan 1000 merkkiä. Please, enter a string: It's a dangerous business, Frodo, going out your door. 3.3. Tulosten esitys Merkkijonon lukemisen jälkeen tulostetaan aluksi lainausmerkkien välissä esikäsitelty merkkijono. Tämän jälkeen tulostetaan omille riveilleen osien lukumäärä ("- The number of parts is x."), osien pituuksien summa ("- The sum of part lengths is x."), osien pituuksien keskiarvo kokonaislukuna ("- The average length of parts is x."), lyhimmän osan pituus ("- The length of the shortest part is x."), toiseksi lyhimmän osan pituus ("- The length of the second shortest part is x."), toiseksi pisimmän osan pituus ("- The length of the second longest part is x.") ja pisimmän osan pituus ("- The length of the longest part is x."). Edellä x tarkoittaa riville tulostettavan tunnusluvun arvoa. Pituuksien keskiarvo lasketaan siten, että osamäärä on liukuluku, joka pyöritetään kokonaisluvuksi Math-luokan round-operaatiolla. "Its a dangerous business Frodo going out your door" - The number of parts is 9. - The sum of part lengths is 42. - The average length of parts is 5. - The length of the shortest part is 1. - The length of the second shortest part is 3. - The length of the second longest part is 8. - The length of the longest part is 9. Lausekielinen ohjelmointi II Syksy 2017 Jorma Laurikkala 3 / 6
3.4. Ohjelman jatkaminen ja lopetus Tietojen tulostuksen jälkeen tiedustellaan omalla rivillään "" ja käyttäjän syöte luetaan välittömästi seuraavalla rivillä. Pieni y-kirjain palauttaa ohjelman merkkijonon lukemiseen. y Please, enter a string: Jos ohjelman esittämään jatkokyselyyn vastataan antamalla syötteenä pieni n- kirjain, niin teksti "See you soon." tulostetaan omalle rivilleen ja ohjelman suoritus lopetetaan. n See you soon. Ohjelma tulostaa omalle rivilleen tekstin "Error!" ja kysyy uudelleen kysymyksen, jos käyttäjä vastaa jatkokysymykseen jollakin muulla merkillä kuin pienellä y- tai n-kirjaimella. Käyttäjän kiusaamista jatketaan kunnes syöte on oikeellinen. k Error! y 4. Koodista Ohjelma kirjoitetaan tuttuun tapaan main-operaation sisään. Koodia ei tarvitse jakaa operaatioiksi, koska tämä asia opetetaan myöhemmin. Omia operaatioita voi toki kirjoittaa niin halutessaan Edistyneempiä tekniikoita, joilla ongelma ratkeaa helpommin, ei saa käyttää. Näihin luetaan esimerkiksi taulukot ja muut tietorakenteet. Javan APIluokkien operaatioiden käyttö on pitkälti kiellettyä. Operaatioista sallittuja ovat vain System.out.println, System.out.print, String-luokan length-, charatja equals-operaatiot ja Math-luokan round-operaatio. Kiellon rikkominen johtaa harjoitustyön hylkäämiseen. Kysy harjoitustyönohjaajaltasi, mikäli olet epävarma mitä saa tehdä ja mitä ei. Koodisi lukee myös ohjaaja. Noudata siis hyvää ohjelmointitapaa [1]: Sisennä koodia luettavuuden parantamiseksi, kommentoi riittävästi, nimeä muuttujat järkevästi, käytä vakioita, pidä rivit riittävän lyhyinä sekä käytä välejä lauseiden sisällä ja erota loogiset kokonaisuudet toisistaan väliriveillä. Sisennä koodi välilyönnein, jotta koodisi näkyisi täsmälleen samanlaisena myös ohjaajan editorissa. Älä käytä sisentämiseen tabulaattoria. Erityisen tärkeää on se, että välilyöntejä ja tabulaattorimerkkejä ei käytetä sekaisin, koska tällöin on täysin varmaa etteivät sisennykset näy ajatellulla tavalla opettajan koneella. Ohjelmassa tulee välttää koodin toistamista. Älä tee erillisiä silmukoita kunkin tunnusluvun laskemiseen, vaan pyri laskemaan kaikki tarpeellinen yhdessä, osat läpikäyvässä silmukassa. Lausekielinen ohjelmointi II Syksy 2017 Jorma Laurikkala 4 / 6
Syötteet luetaan In-luokan avulla. Älä käytä muita menetelmiä syötteiden lukemiseen. Ohjelman nimen tulee olla StringStats, jolloin lähdekoodin tulee olla StringStats.java-nimisessä tekstitiedostossa. Älä kirjoita ohjelmaan ikuisia silmukoita tai käytä break-lausetta. 5. Dokumentointi Harjoitustyöstä kirjoitetaan dokumentti, jonka tulee sisältää seuraavat asiat: 1. Kansilehdellä tekijän nimi, opiskelijanumero, sähköpostiosoite, yksikkö ja tutkinto-ohjelma. Sivun keskellä tulisi olla suuremmalla fontilla dokumentin nimi. Kurssin kotisivuilla julkaistaan esimerkinomainen kansilehti. 2. Korkeintaan puolen sivun mittainen kuvaus ohjelman toiminnasta vapaamuotoisena tekstinä. 3. Omia ajatuksia. Esimerkiksi: Oliko työ helppo, sopiva vai vaikea? Jos helppo tai vaikea, niin miksi? Mitä uutta opit? Oliko työstä mitään hyötyä sinulle? Montako tuntia työn tekemiseen meni? Dokumentin leipäteksti kirjoitetaan 12 pisteen fontilla ja yhdellä rivinvälillä. Dokumentin kirjoitus tekstinkäsittelyohjelmalla ja kieliasun tarkistus ohjelman oikolukutoiminnolla on suotavaa. Valmis teksti kannattaa lukea ennen palautusta. Dokumentti on palautettava PDF-muodossa. Muut tiedostomuodot eivät kelpaa. Luvussa 7 ja kurssin verkkosivuilla kerrotaan tarkemmin dokumentin ja koodin palauttamisesta. 6. Ohjaus ja tarkistus Harjoitusryhmien vetäjät vastaavat pääsääntöisesti ryhmäläistensä töiden ohjauksesta ja tarkistuksesta. (Tuntiopettajat tarkistavat kurssin vastuuopettajan ryhmäläisten harjoitustyöt.) Apua saa sähköpostitse sekä harjoitusten yhteydessä. Ohjaajat ovat myös henkilökohtaisesti yliopistolla tavattavissa myöhemmin julkaistavina aikoina. Kurssin vastuuopettaja auttaa harjoitustyöongelmissa myös muitakin kuin oman ryhmänsä opiskelijoita. Pyri kuitenkin ottamaan ongelmatilanteissa yhteys ensin oman harjoitusryhmän vetäjään, koska vastuuopettajalla on toisinaan kiire. Muista myös, että tehtävänantoon ja Javan piirteiden käyttöön liittyvissä epävarmoissa tilanteissa kannattaa aina kysyä ohjaajalta, koska kysyminen on parempi vaihtoehto kuin työn mahdollinen hylkäys. Lausekielinen ohjelmointi II Syksy 2017 Jorma Laurikkala 5 / 6
7. Harjoitustyön palautus Ohjelma ja dokumentti täytyy palauttaa sähköisesti keskiviikkoon 8.11.2017 klo 16.00 mennessä WETO-järjestelmään. Tarkemmat palautusohjeet julkaistaan kurssin verkkosivuilla. Harjoitustöiden toiminnallisuus tarkistetaan WETO-järjestelmällä, joka vertailee automaattisesti mallivastauksen ja opiskelijoiden ratkaisujen tulosteita. Tästä syystä edellä annettuja tulostemäärittelyjä on seurattava merkilleen. Automaattinen vertailu vähentää rutiininomaista testaustyötä, jolloin opettajille jää enemmän aikaa mielekkäämpään työhön eli ohjelman rakenteen ja tyylin tutkimiseen. Opiskelijat hyötyvät tästä perusteellisempien kommenttien muodossa. Lisäaikaa työn tekoon voi saada muutaman päivän vain hyvästä syystä. Lisäajasta on sovittava harjoitusryhmän vetäjän kanssa ajoissa eli viimeistään päivää tai paria ennen palautuksen takarajaa. Ennen palautusta on syytä varmistaa, että dokumentissa on mukana kaikki edellä mainitut kohdat. Lisäksi kannattaa tarkistaa, että ohjelma toimii varmasti oikein viimeisimpien muutosten jälkeen. 8. Harjoitustyön arvostelu Harjoitustyöt arvostellaan asteikolla hyväksytty/hylätty. Harjoitusryhmän vetäjä ilmoittaa työn kohtalosta sähköpostilla, jossa on myös tarkempia kommentteja ohjelman tyylistä (rakenne ja hyvä ohjelmointitapa). Hylkäyksen perusteena voi olla ohjelman virheellinen toiminta, hyvän ohjelmointitavan noudattamatta jättäminen, harjoitustyön teossa kiellettyjen Javan ominaisuuksien käyttö (esimerkiksi taulukko), huono dokumentti tai plagiointi. Plagiointiin liittyy sanktio, joka koskee molempia opiskelijoita. Toiselta opiskelijalta tämän tietämättä kopioidun koodin käyttö johtaa kopioijan koko kurssisuorituksen hylkäämiseen. Hylätty työ on korjattava pääsääntöisesti viikon sisällä hylkäyksestä. Työn voi palauttaa opettajan tarkistettavaksi korkeintaan neljä kertaa ilman pakottavaa syytä lisäpalautuksiin Lähteet [1] J. Laurikkala: Lausekielinen ohjelmointi -kurssin luentorunko, luku 14, http://www.sis.uta.fi/~laki1/luennot/luento08/ (Luettu viimeksi 16.10.2017.) Lausekielinen ohjelmointi II Syksy 2017 Jorma Laurikkala 6 / 6