Ohjelmointityö 65 Tekstinmuotoilu ohjelma. Dokumentaatio. Aki Heikkinen (155394)



Samankaltaiset tiedostot
Ohjelmassa henkilön etunimi ja sukunimi luetaan kahteen muuttujaan seuraavasti:

Ohjelmointityö 3. Mikko Laamanen

Ohjelmoinnin perusteet Y Python

Ohjelmoinnin perusteet Y Python

5. HelloWorld-ohjelma 5.1

Metodien tekeminen Javalla

Java-kielen perusteita

Ohjelmoinnin perusteet Y Python

Rinnakkaisohjelmointi kurssi. Opintopiiri työskentelyn raportti

Ohjelmointitaito (ict1td002, 12 op) Kevät Java-ohjelmoinnin alkeita. Tietokoneohjelma. Raine Kauppinen

Sisällys. 12. Näppäimistöltä lukeminen. Yleistä. Yleistä

Ohjelmointi 2 / 2010 Välikoe / 26.3

Tietojen syöttäminen ohjelmalle. Tietojen syöttäminen ohjelmalle Scanner-luokan avulla

Sisältö Johdanto. Tiedostojen lukeminen. Tiedostojen kirjoittaminen. 26.2

1. Kun käyttäjä antaa nollan, niin ei tulosteta enää tuloa 2. Hyväksy käyttäjältä luku vain joltain tietyltä väliltä (esim tai )

Sisältö. Johdanto. Tiedostojen lukeminen. Tiedostojen kirjoittaminen. 6.2

Sisältö. 2. Taulukot. Yleistä. Yleistä

Yleistä. Nyt käsitellään vain taulukko (array), joka on saman tyyppisten muuttujien eli alkioiden (element) kokoelma.

Ohjelmoinnin perusteet Y Python

Sisältö. Johdanto. Tiedostojen lukeminen. Tiedostojen kirjoittaminen. 6.2

Ohjelmoinnin perusteet Y Python

Java-kielen perusteet

Sisältö. 22. Taulukot. Yleistä. Yleistä

Informaatioteknologian laitos Olio-ohjelmoinnin perusteet / Salo

8. Näppäimistöltä lukeminen 8.1

12. Näppäimistöltä lukeminen 12.1

Ohjelmointi 1 / 2009 syksy Tentti / 18.12

5. HelloWorld-ohjelma 5.1

Ohjelmoinnin jatkokurssi, kurssikoe

Metodit. Metodien määrittely. Metodin parametrit ja paluuarvo. Metodien suorittaminen eli kutsuminen. Metodien kuormittaminen

Java-kielen perusteita

Ohjelmointitaito (ict1td002, 12 op) Kevät Java-ohjelmoinnin alkeita. Tietokoneohjelma. Raine Kauppinen

Ohjelmoinnin perusteet Y Python

Tässä tehtävässä käsittelet metodeja, listoja sekä alkulukuja (englanniksi prime ).

Taulukot. Taulukon määrittely ja käyttö. Taulukko metodin parametrina. Taulukon sisällön kopiointi toiseen taulukkoon. Taulukon lajittelu

// Tulostetaan double-tyyppiseen muuttujaan "hinta" tallennettu // kertalipun hinta ja vaihdetaan riviä. System.out.printf("%.1f euros.

14. Poikkeukset 14.1

Ohjelmoinnin perusteet Y Python

// Tulostetaan double-tyyppiseen muuttujaan "hinta" tallennettu // kertalipun hinta ja vaihdetaan riviä. System.out.printf("%.1f euros.

8. Näppäimistöltä lukeminen 8.1

Opintojakso TT00AA11 Ohjelmoinnin jatko (Java): 3 op. Poikkeukset ja tietovirrat: Virhetilanteiden ja syötevirtojen käsittely

Ohjelmoinnin perusteet, syksy 2006

7. Näytölle tulostaminen 7.1

Ohjelmoinnin perusteet, kurssikoe

Sisällys. 14. Poikkeukset. Johdanto. Johdanto

Toinen harjoitustyö. ASCII-grafiikkaa 2017

Taulukoiden käsittely Javalla

Olio-ohjelmointi Javalla

Ohjelmointi 2 / 2008 Välikoe / Pöytätestaa seuraava ohjelma.

Pythonin Kertaus. Cse-a1130. Tietotekniikka Sovelluksissa. Versio 0.01b

Listarakenne (ArrayList-luokka)

Luokka Murtoluku uudelleen. Kirjoitetaan luokka Murtoluku uudelleen niin, että murtolukujen sieventäminen on mahdollista.

Javan perusteet. Ohjelman tehtävät: tietojen syöttö, lukeminen prosessointi, halutun informaation tulostaminen tulostus tiedon varastointi

Sisällys. 14. Poikkeukset. Johdanto. Johdanto

ITKP102 Ohjelmointi 1 (6 op)

14. Poikkeukset 14.1

Tietorakenteet. JAVA-OHJELMOINTI Osa 5: Tietorakenteita. Sisällys. Merkkijonot (String) Luokka String. Metodeja (public)

Rajapinta (interface)

Ohjelmoinnin perusteet Y Python

Taulukot. Jukka Harju, Jukka Juslin

ITKP102 Ohjelmointi 1 (6 op)

2. Lisää Java-ohjelmoinnin alkeita. Muuttuja ja viittausmuuttuja (1/4) Muuttuja ja viittausmuuttuja (2/4)

Ohjelmoinnin perusteet Y Python

Harjoitus 5 (viikko 48)

Kompositio. Mikä komposition on? Kompositio vs. yhteyssuhde Kompositio Javalla Konstruktorit set-ja get-metodit tostring-metodi Pääohjelma

14. Hyvä ohjelmointitapa 14.1

Harjoitus Olkoon olemassa luokat Lintu ja Pelikaani seuraavasti:

17. Javan omat luokat 17.1

1. Mitä tehdään ensiksi?

1 Tehtävän kuvaus ja analysointi

Opintojakso TT00AA11 Ohjelmoinnin jatko (Java): 3 op Taulukot & Periytyminen

11. Javan toistorakenteet 11.1

Ohjelmoinnin perusteet Y Python

Mitä poikkeuskäsittely tarkoittaa?

Ohjelmoinnin perusteet Y Python

4. Luokan testaus ja käyttö olion kautta 4.1

Ohjelmointi 2, välikoe

Kääreluokat (oppikirjan luku 9.4) (Wrapper-classes)

12. Javan toistorakenteet 12.1

Tietokannat II -kurssin harjoitustyö

Kirjoita, tallenna, käännä ja suorita alla esitelty ohjelma, joka tervehtii käyttäjäänsä.

Java-kielen perusteita

815338A Ohjelmointikielten periaatteet Harjoitus 2 vastaukset

List-luokan soveltamista. Listaan lisääminen Listan läpikäynti Listasta etsiminen Listan sisällön muuttaminen Listasta poistaminen Listan kopioiminen

20. Javan omat luokat 20.1

Ohjelmoinnin perusteet Y Python

ITKP102 Ohjelmointi 1 (6 op), arvosteluraportti

Sisällys. 20. Javan omat luokat. Java API. Pakkaukset. java\lang

Lausekielinen ohjelmointi II Ensimmäinen harjoitustyö

Interaktiivinen tarinankerronta

Ohjelmointi 1 Taulukot ja merkkijonot

Kirjoita oma versio funktioista strcpy ja strcat, jotka saavat parametrinaan kaksi merkkiosoitinta.

Ohjelmoinnin perusteet Y Python

Maastotietokannan torrent-jakelun shapefile-tiedostojen purkaminen zip-arkistoista Windows-komentojonoilla

Poikkeustenkäsittely

Tietorakenteet ja algoritmit syksy Laskuharjoitus 1

13. Hyvä ohjelmointitapa (osa 1) 13.1

IDL - proseduurit. ATK tähtitieteessä. IDL - proseduurit

ATK tähtitieteessä. Osa 3 - IDL proseduurit ja rakenteet. 18. syyskuuta 2014

Harjoitus 2 (viikko 45)

Transkriptio:

Ohjelmointityö 65 Tekstinmuotoilu ohjelma Dokumentaatio Aki Heikkinen (155394) 15.6.2007

Sisällysluettelo 1. Tehtävän määrittely ja ratkaisuperiaate... 1 1.1. Tehtävän määrittely... 1 1.2. Ratkaisuperiaate... 2 2. Ohjelmankäyttöohje... 3 2.1. Syötteet ja tulosteet... 4 2.1.1. Tiedoston nimi... 4 2.1.2. Tulostusrivinkoko... 4 2.1.3. Kappaleen alkutyhjän määrä... 4 2.1.4. Tavuttaminen... 4 2.1.5. Lopputulostus... 4 2.2. Ohjelman sisältämät tarkastukset ja virheilmoitukset... 4 2.2.1. Tiedoston nimi... 4 2.2.1.1 Tyhjä tiedosto... 5 2.2.2. Tulostusrivinkoko... 5 2.2.3. Kappaleen alkutyhjän määrä... 5 2.2.4. Tavuttaminen... 5 2.3. Ohjelman rajoitukset... 5 2.3.1. Tiedoston nimi... 5 2.3.2. Tulostusrivinkoko... 5 2.3.3. Kappaleen alkutyhjän määrä... 5 2.3.4. Tavuttaminen... 5 2.3.5. Luettava tekstitiedosto... 5 2.4. Ajo-ohje... 6 3. Ohjelman toiminta... 6 3.1. Tietorakenteet... 6 3.1.1. Vector sanat... 6 3.1.2. Vector rivit... 6 3.1.3. Kuva tietorakenteista... 7 3.2. Ohjelman rakenne... 7 3.2.1. Uusi kappale... 8 3.2.2. Rivin ylitys... 9 3.2.3. Tavuttaminen... 9 3.2.4. Ohjelma pseudokoodina... 10

3.2.5. Kuva... 11 3.3 Luokat ja niiden metodit... 12 3.3.1. public class ohjelmointityo65... 12 3.3.1.1. public static void main()... 12 3.3.2. public class Lue... 12 3.3.2.1. public String luestringsyote()... 12 3.3.2.1. public int lueintsyote()... 12 3.3.3. public class LueTiedosto... 12 3.3.3.1. public String luetiedosto()... 12 3.3.4. public class Muokkaa... 12 3.3.4.1. static Object teesana()... 13 3.3.4.2. static Vector muutasanoiksi()... 13 3.3.4.3. public Vector luouusiteksti()... 13 3.3.4.4. public String[] teetavutus()... 13 3.3.5. public class Tulosta... 14 3.3.5.1. public void tulostateksti()... 14 3.4. Muutosohjeet... 14 3.4.1. Tiedoston nimi... 14 3.4.2. Tulostusrivinkoko... 14 3.4.3. Kappaleen alkutyhjän määrä... 14 4. Testaus... 15 4.1. Ohjelman kysyessä anna luettavan tiedoston nimeä... 15 4.2. Ohjelman kysyessä anna tulosterivin koko (30-75)... 15 4.3. Ohjelman kysyessä anna kappaleen alkutyhjan maara (1-5)... 16 4.4. Tavuttaminen... 16 4.5. Tekstin muotoilu.... 17 4.5.1 Läpiajo testaukset 1... 17 4.5.2 Läpiajo testaukset 2... 18 4.5.3 Läpiajo testaukset 3... 19 4.5.4 Läpiajo testaukset 4... 19 4.5.5 Läpiajo testaukset 5... 20 Liitteet: Tehtäväpaperi, Projektisuunnitelma, Ohjelmalistaus

1 1. Tehtävän määrittely ja ratkaisuperiaate Ohjelmointityö on tekstinmuokkaus ohjelma, joka lukee käyttäjän syöttämän tekstitiedoston (.txt) ja muotoilee sen uudeksi tekstikokonaisuudeksi käyttäjän määrittämien arvojen, kuten tulostusrivin koon ja kappaleen alkutyhjän, mukaan. Ohjelma kysyy myös käyttäjältä tarvittaessa sanojen tavuttamisen. Lopuksi ohjelma tulostaa muokatun tekstin. 1.1 Tehtävän määrittely Ohjelman tarkoitus on lukea teksti ja muotoilla se uudeksi kokonaisuudeksi. Ohjelma kysyy käyttäjältä luettavan tiedoston nimeä, jonka tulee olla.txt loppupäätteellinen. Työssä on mukana valmistiedosto TEKSTI.txt, mutta haluttaessa ohjelmaan voi syöttää minkä tahansa muun.txt tiedoston. Tekstiä muotoillaan kolmella eri tavalla: (1) Luodaan uudet kappaleenalut kun tekstissä tulee vastaan * merkkiyhdistelmä. Tämä tarkoittaa sitä, että uusi kappale alkaa uudelta riviltä ja sen edessä ja tyhjää käyttäjän syötteen mukaisesti. (2) Teksti jäsennellään siten, että yksikään tulostusrivi ei ylitä käyttäjän syöttämää tulostusrivin kokoa (merkkeinä). Kun tulostusrivi ylitetään, niin voidaan toimia kahdella eri tavalla: (a) Jos sana on maksimissaan 12 merkkiä pitkä, niin siirrytään uudelle riville tulostaen sana ja jatkaen normaalisti sen jälkeen tai (b) tavuttamalla sana (katso alla), jos se on yli 12 merkkiä pitkä. (3) Tavuttaminen on ohjelman kolmas muotoiluominaisuus. Siinä ohjelma pyytää käyttäjää tavuttamaan sanan haluamastaan kohdasta, jolloin sana jaetaan kahdelle tulostusriville tavutusmerkin kohdalta. Huomautus: Ohjelma esittää mistä kohtaa sana on ylittänyt tulostusrivin, mutta jos käyttäjä haluaa tavuttaa sanan siitä kohdasta tai sen jälkeen, tulostaa ohjelma koko sanan suoraan uudelle riville. 1

2 1.2 Ratkaisuperiaate Ohjelma kysyy käyttäjältä halutun tiedoston nimeä ja tarkistaa onko tiedosto olemassa ja että siinä on jotain sisältöä. Jos tiedosta ei ole tai se on tyhjä, niin ohjelma ilmoittaa siitä käyttäjälle ja ohjelma lopettaa toimintansa. Onnistuneesti avatusta ja luetusta tekstistä tehdään yksi pitkä merkkijono kokonaisuus muotoilua varten. Sen jälkeen ohjelma kysyy käyttäjältä tulostusrivin kokoa, jonka tulee olla kokonaislukuarvo 30 ja 75 väliltä. Virheellisissä syötteissä ohjelma pyytää käyttäjää syöttämään arvon uudestaan. Tämän jälkeen ohjelma kysyy käyttäjältä kappaleen alkutyhjän määrää, jonka tulee olla kokonaisluku arvo 1 ja 5 väliltä. Jos käyttäjä syöttää virheellisen arvon, niin ohjelma pyytää käyttäjää syöttämään arvon uudestaan. Kun tarpeelliset syötteet (katso yllä) on saatu, niin ohjelma alkaa muotoilemaan määritetyn tiedoston sisältöä uudeksi tekstikokonaisuudeksi. Muotoilu on kolmiosainen toiminpidekokonaisuus. (1) Avattu teksti erotellaan sanoiksi välilyöntien mukaan. Sanat muodostuu kahden välilyönnin kokonaisuudesta, joiden keskellä on itse sana (poikkeus on viimeinen sana). (2) Kun sanat ovat eroteltu toisistaan, aletaan niitä kokoamaan uudeksi tekstikokonaisuudeksi käyttäjän antamien arvojen mukaan (tulostusrivin koko ja kappaleen alkutyhjän määrä). Sanoja asetataan toistensa perään alkuperäisessä järjestyksessä erottaen ne välilyönnillä. Tätä jatketaan kunnes tulostusrivinkoko tulee täyteen tai se ylitetään, tai kun kappaleenjako merkki ( *) on löydetty. Uudet muotoillut tekstikokonaisuudet tallennetaan riveittäin. (a) Kun kappaleenjakomerkki on löydetty, niin siirrytään suoraan uudelle riville ja aletaan liittää sanoja toisiinsa kuten yllämainittu. (b) Kun tulostusrivinkoko ylitetään, niin ohjelma tarkastaa onko ylittävä sana yli 12 merkkiä pitkä kokonaisuus, jos näin ei ole, niin siirrytään suoraan uudelle riville ja jatketaan tavallisesti kuten yllämainittu. Jos sana on yli 12 merkkiä pitkä, niin silloin suoritetaan sanan tavutus (katso alla). (3) Tavuttamisessa ohjelma ilmoittaa käyttäjälle mistä kohtaa sana ylittää tulostusrivin koon ja pyytää käyttäjää tavuttamaan sanan yhdestä kohdasta. Käyttäjän tulee kirjoittaa sana syötteenä, ja liittää siihen yksi tavutusmerkki (-). Sanan tulee olla oikeinkirjoitettu ja se saa olla tavutettu vain yhdestä kohtaa, muuten ohjelma pyytää käyttäjää syöttämään sen uudestaan. 2

3 Kun kaikki sanat on liitetty toisiinsa ja mahdolliset tavuttamiset on suoritettu, niin uusi, muotoiltu tekstikokonaisuus tulostetaan rivettäin. 2. Ohjelman käyttöohje Ohjelman saa avattua komentorivillä komennolla java ohjelmontityo65. Ohjelma kysyy aluksi luettavan tiedoston nimeä, johon käyttäjän tulee antaa haluamansa tiedostonnimi ilman sen lopputunnistetta (huomaa, että tiedosto tulee olla.txt lopputunnisteinen). Esimerkiksi jos käyttäjä haluaa lukea ohjelmalla TESTI.txt tiedoston, niin käyttäjän tulee kirjoittaa ohjelman kysyessä luettavaa tekstiä: testi. Huomaa kuitenkin, ettei isoilla ja pienillä kirjaimilla ole väliä kun kirjoitat tiedostonnimeä, mutta luettavan tiedoston tulee olla samassa kansiossa, missä itse ohjelma sijaitsee. Jos käyttäjän asettamaa tiedostoa ei löydy tai se on kirjoitettu väärin, ilmoittaa ohjelma tästä käyttäjälle ja sulkee itsensä. Jos haluttu tiedosto on olemassa, mutta se on tyhjä, niin ohjelma ilmoittaa tästä myös käyttäjälle lopettaen itsensä. Onnistuneesti luetun tiedoston jälkeen ohjelma pyytää käyttäjää syöttämään tulostusrivin kokoon, johon käyttäjän tulee antaa kokonaisluku arvo väliltä 30 ja 75. Tämä arvo on tulostuksessa käytettävä maksimaalinen merkkien määrä jokaisella rivillä. Jos käyttäjä asettaa vääränlaisen syötteen, niin ohjelma ilmoittaa tästä käyttäjälle ja pyytää käyttäjää syöttämään arvon uudestaan. Tämä jatkuu kunnes käyttäjä on syöttänyt hyväksyttävän arvon. Seuraavaksi ohjelma pyytää käyttäjää syöttämään kappaleiden alkutyhjän määrä. Tämän syötteen tulee olla kokonaisluku väliltä 1 ja 5. Tämä arvo on tulostuksessa käytettävä kappaleiden alkutyhjän määrä välilyönteinä. Jos käyttäjä syöttää vääränlaisen syötteen, niin ohjelma ilmoittaa tästä käyttäjälle ja pyytää käyttäjää syöttämään uuden arvon. Tämä jatkuu kunnes käyttäjä on syöttänyt hyväksyttävän arvon. Näiden kolmen syötteen jälkeen ohjelma muotoilee käyttäjän määittämän tiedoston tekstisisällön syötettyjen arvojen mukaan. Tämän prosessin aikana ohjelma voi kysyä käyttäjältä joidenkin sanojen tavuttamisen, jossa käyttäjän tulee syöttää ohjelma ilmoittama sana yhden tavutusmerkin ( - ) kanssa. Väärinkirjoitetusta tai puutteellisesta sanasta ohjelma pyytää käyttäjää kirjoittamaan ja tavuttamaan saman sanan uudestaan kunnes sana on oikein kirjoitettu ja sisältää yhden tavutusmerkin. Tässä vaiheessa isoilla ja pienillä kirjaimilla on väliä. Kun koko teksti on käyty läpi ja muotoiltu, niin ohjelma tulostaa sen. 3

4 2.1 Syötteet ja tulosteet 2.1.1 Tiedoston nimi: Ohjelma pyytää käyttäjää syöttämään halutun tiedoston nimeä seuraavasti Anna luettavan tiedoston nimi:. Syöte annetaan komentoriville ja sen tulee olla syötetty ilman lopputunnistetta (esimerkiksi.txt), mutta isoilla tai pienillä kirjaimilla ei ole väliä. Tiedoston tulee olla samassa kansiossa, missä itse ohjelma sijaitsee, muuten tapahtuu virhe. 2.1.2 Tulostusrivinkoko: Kun ohjelma ilmoittaa käyttäjelle seuraavasti Anna tulosterivin koko (30-75): Käyttäjän tulee syöttää komentoriviä käyttäen tulostusrivin koko, joka saa olla 30 ja 75 välillä oleva kokonaisluku. 2.1.3 Kappaleen alkutyhjän määrä: Seuraavaksi ohjelma ilmoittaa Anna kappaleen alkutyhjien määrä (1-5):, jolloin käyttäjän tulee antaa kokonaislukuarvo 1 ja 5 väliltä komentoriville. 2.1.4 Tavuttaminen: Tarpeen vaatiessa ohjelma ilmoittaa käyttäjälle yli 12 merkkisen sanan ylittäneen tulostusrivin seuraavasti: Tulostusrivin koko loppui kesken kohdassa ^ Tavuta sana yhdestä kohtaa. Ohjelma ilmoittaa myös kohdan sanassa mistä tulostusrivinkoko ylitetään. Samalla ohjelma pyytää käyttäjää suorittamaan tavuttamisen. Tällöin käyttäjän tulee kirjoittaa komentoriviä käyttäen ohjelman ilmoittama sana yhden (ja vain yhen) tavutusmerkin (-) kanssa. Virheellisen tai väärinkirjoitetun sanan syöttämisestä syntyy virhe. 2.1.5 Lopputulostus: Ohjelma tulostaa muotoillun tekstin näytölle kokonaisuudessaan. 2.2 Ohjelman sisältämät tarkastukset ja virheilmoitukset 2.2.1 Tiedoston nimi: Jos ohjelma ei löydä tiedostoa käyttäjän syöttämän tiedostonnimen mukaan, niin ohjelma ilmoittaa: Tiedostoa ei löytynyt! Ohjelma suljetaan. ja ohjelma sulkeutuu ilmoituksen jälkeen. Virhe voi johtua siitä, että käyttäjä on kirjoittanut luettavan tiedoston väärin tai on lisännyt tiedoston loppupääteen syötteeseen mukaan. Huomaa kuitenkin, ettei isoilla ja pienillä kirjaimilla ole väliä tässä vaiheessa. Virhe voi johtua myös siitä, ettei tiedosto ole samassa kansiossa, missä ohjelma sijaitsee. 4

5 2.2.1.1 Jos tiedosto löytyi, mutta se on tyhjä, niin ohjelma ilmoittaa virheilmoituksen: Tiedosto on tyhjä! Ohjelma suljetaan. ja ohjelma sulkeutuu ilmoituksen jälkeen. Syy tälle on se, että tiedosto on täysin tyhjä, eikä siinä ole minkäänlaisia merkkiä. 2.2.2 Tulostusrivinkoko: Jos käyttäjä antaa tässä vaiheessa syötteen, joka on sallittujen arvojen ulkopuolelta, eli pienempää kuin 30 tai isompaa kuin 75, niin ohjelma antaa virheilmoituksen: Virheellinen syöte, anna uusi (30 75): Virheen sattuminen johtuu siitä, jos käyttäjän antama syöte ei ole kokonaisluku tai se on yllämainittujen raja-arvojen ulkopuolelta. 2.2.3 Kappaleen alkutyhjän määrä: Jos käyttäjä antaa tässä vaiheessa syötteen, joka on sallittujen arvojen ulkopuolelta, eli pienempää kuin 1 tai isompaa kuin 5, niin ohjelma antaa virheilmoituksen: Virheellinen syöte, anna uusi (1 5): Virheen sattuminen johtuu siitä, jos käyttäjän antama syöte ei ole kokonaisluku tai se on yllämainittujen raja-arvojen ulkopuolelta. 2.2.4 Tavuttaminen: Virheellinen syöte tässä vaiheessa johtuu siitä, että käyttäjä ei ole kirjoittanut ohjelman antamaa, tavutettavaa sanaa oikein, tai siitä puuttuu yksi tavutusmerkki (-), tai että siinä on useampi kuin yksi tavutusmerkki. Isot kirjaimet merkitset tässä vaiheessa, joten jos esimerkiksi sana alkaa isolla kirjaimella tulee se myös kirjoittaa isolla kirjaimella alkavaksi. Ohjelman antama virheilmoitus tässä vaiheessa on seuraavanlainen: Virhe! Olet kirjoittanut sanan väärin, yritä uudelleen. 2.3 Ohjelman rajoitukset 2.3.1 Tiedoston nimi: Syötettävän tiedoston tulee olla.txt loppupäätteellinen, mutta käyttäjän antamassa syötteessä ei saa olla mukana sen loppupäätettä. 2.3.2 Tulostusrivinkoko: Syöte saa olla 30 ja 75 väliltä oleva kokonaisluku. 2.3.3 Kappaleen alkutyhjän määrä: Syöte saa olla 1 ja 5 väliltä oleva kokonaisluku. 2.3.4 Tavuttaminen: Tavuttaminen tulee olla tehty vain yhdestä kohtaa - merkillä. 2.3.5 Luettava tekstitiedosto: Ohjelma ei kykene käsittelemään ääkkösiä, joten luettavan tekstitiedoston sisällössä ei tulisi olla yhtään ä-, ö- tai å-kirjainta. 5

6 2.4 Ajo-ohje Ohjelman lähdekieliset luokat ovat Lue.java, LueTiedosto.java, Muokkaa.java, ohjelmatyo65.java ja Tulosta.java. Suorituskelpoisten tiedoston nimet ovat Lue.class, LueTiedosto.class, Muokkaa.class, ohjelmatyo65.class ja Tulosta.class, jossa ohjelmointityo65.class on pääohjelmaluokka. Ohjelman mukana on valmiiksi luotu tekstitiedosto TEKSTI.txt, mutta ohjelma kykenee käyttämään myös muita.txt tiedostoja. Ohjelman kääntäminen lähdekielisestä suorituskelpoiseksi tapahtuu antamalla komentoriville komento javac ohjelmointityo65.java jolloin kaikkien yllämainittujen.java tiedostojen tulee olla samassa kansiossa, missä kääntäminen tapahtuu. Jos tietokone ei anna virheilmoitusta, niin kääntäminen on onnistunut ja jokaisesta yllämainitusta.java päätteellisestä tiedostosta on tehty.class päätteelliset tiedostot Suorittaminen tapahtuu komentorivillä komennolla java ohjelmointityo65 ja sen aikana kaikki yllämainitut.class pääteelliset tiedostot tulevat olla samassa kansiossa. Tämän lisäksi samassa kansiossa tulee olla myös jokin.txt päätteellinen tekstitiedosto, jota halutaan käyttää. 3 Ohjelman toiminta 3.1 Tietorakenteet 3.1.1 Vector sanat tietorakenteeseen tallennetaan luetun tiedoston merkkijonosta eritellyt sanat, täten vektori sisältää Object luokan olioita, joita on tarkoitettu käytettävän String arvoina Object luokan.tostring() metodin kautta. Jokainen sana on omassa alkiossaan. Vektorin sisältö luodaan Muokkaa luokan metodissa muutasanoiksi(), jossa Vector palautus toimii tilapäisenä tietorakenteena, johon sanat kootaan. Tämän tietorakenteen sisällöstä kootaan uuden tekstikokonaisuuden rivien sisältö. 3.1.2 Vector rivit tietorakenteeseen tallennetaan eritellyistä sanoista kootut uudet kokonaisuudet riveittäin. Yksi uudelleen muotoiltu rivi on oma alkionsa. Vektori sisältää Object luokan olioita, joita on tarkoitettu käytettävän String arvoina Object luokan.tostring() metodin kautta. Vektorin sisältä luodaan Muokkaa luokan 6

7 metodissa teeuusiteksti(), jossa Vector palautus toimii tilapäisenä tietorakenteena, johon kootut rivit tallennetaan. Tämän tietorakenteen sisältö on lopullinen muotoiltu tekstikokonaisuus. 3.1.3 Kuva tietorakenteista Luettava tekstitiedosto Luettu teksti yhtenä pitkänä merkkijonona Vector sanat Teksti eritelty sanoiksi Vector rivit Yksittäiset sanat liitetty uudeksi tekstikokonaisuudeksi, riveittäin 3.2 Ohjelman rakenne Tärkein ja keskeisin rakenne ohjelmassa on tekstin muotoilu, joten se käsitellään tässä yksityiskohtaisemmin. Ennen tekstin käsittelyä ohjelma on lukenut tekstitiedoston ja liittänyt sen sisällön yhdeksi pitkäksi merkkijonokokonaisuudeksi. Jokaiseen alkuperäisen tekstin rivinalkuun ohjelma kirjoittaa uuden välilyönnin ja liittää sen kokonaisuudessaan edeltävän rivin perään. Esimerkiksi seuraavanlaisesta alkuperäisestä tekstistä 7

8 Laihajussi juoksi metsään piiloon itseään, koska on pelkuri. saamme seuraavanlaisen yhden pitkän merkkijonon, jossa _ merkki tarkoittaa ohjelman asettamia uusia välilyöntejä: _Laihajussi juoksi metsään_piiloon itseään,_koska on pelkuri. Tekstin muotoilussa luotu pitkä merkkijonokokonaisuus otetaan käsittelyyn ja siitä erotellaan sanat toisistaan käymällä merkkijonoa läpi. Läpikäynti tapahtuu merkki kerrallaan, etsien välilyöntejä, kun ensimmäinen välilyönti on löytynyt, sen kohta merkataan ylös muistiin ja jatketaan etsintää kunnes toinen välilyönti on löytynyt. Näiden kahden välilyönnin väliin jäävät merkit muodostavat yhden sanan ja se kirjoitetaan omaksi alkiokseen Vector sanat tietorakenteeseen. Huomaa, että kaikki erikoismerkit liitetään automaattisesti sanaan, jos erikoismerkkien ja sanan välillä ei ole välilyöntiä. Seuraavaksi kun kaikki sanat on eritelty toisistaan ja tallennettu omiin alkioihinsa ohjelma alkaa käymään sanoja läpi yksitellen alkuperäisessä tallennusjärjestyksessä ja liittämään niitä toistensa perään, erottaen ne toisistaan välilyönnillä, muodostaen täten uusia rivikokonaisuuksia kunnes tapahtuu yksi seuraavista: (a) Löydetään * merkki, joka tarkoittaa uuden kappaleen alkua. Katso kohta 3.2.1. (b) Jos uuden sanan, jonka pituus on maksimissaan 12 merkkiä, liittäminen nykyiseen riviin ylittäisi tulostusrivin koon. Katso kohta 3.2.2 (c) Jos uuden sanan, jonka pituus on yli 12 merkkiä, liittäminen nykyiseen riviin ylittäisi tulostusrivin koon. Tällöin tapahtuu tavuttamistoiminpide. Katso kohta 3.2.3 Kaikkien tapauksen jälkeen ohjelma jatkaa uuden rivikokonaisuuden luontia ja tallentaan aikaisemman rivikokonaisuuden omaksi alkiokseen Vector rivit tietorakenteeseen. Katso kohdan 3.1 kuva. 3.2.1 Uusi kappale: Kun * merkkikokonaisuus on löydetty, niin aletaan suoraan luomaan uutta riviä, tallentaen aikaisempi rivikokonaisuus omaan alkioonsa. Uuden rivin alkuun luodaan käyttäjän määrittämän kappaleen alkutyhjän verran välilyöntejä, ja sen jälkeen jatkaen normaalisti. Jos * merkki on ollut kiinni sanassa, niin se on poistettu sanasta, ennen 8

9 sanan kirjoittamista rivikokonaisuuteen. Huomaa, että uusi kappale aloitetaan vasta seuraavasta sanasta kappaleenjakomerkin jälkeen. Täten, jos * merkki on esimerkiksi sanan alussa tai keskellä, niin uusi kappale alkaa vasta seuraavasta sanasta. 3.2.2 Rivin ylittäminen: Kun tulostusrivi ylitettäisiin sanalla, joka on maksimissaan 12 merkkiä pitkä, niin silloin aikaisempi rivikokonaisuus tallennetaan omaan alkioonsa ja uutta rivikokonaisuutta aletaan tekemään aloittaen paraikaa käsitteillä olevasta sanasta. Toisinsanen käsitteillä oleva sana siirretään uudelle riville suoraan. 3.2.3 Tavuttaminen: Kun tulostusrivi ylitettäisiin sanalla, joka on yli 12 merkkiä pitkä, niin silloin suoritetaan tavuttamistoiminpide. Tällöin ohjelma laskee mistä kohtaa sana ylittää tulostusrivin ja ilmoittaa käsitteillä olevan sanan ja tulostusrivin ylittävän kohdan. Käyttäjän tulee kirjoittaa ohjelman ilmoittama sana yhdelle tavutusmerkillä (-) varustettuna. Ohjelma tarkastaa tavutuksen oikeellisuuden seuraavilla tavoilla: (a) Tavutetun sanan tulee olla yhtä merkkiä alkuperäistä pidempi. Jos näin ei ole, niin silloin joko sana on kirjoittu väärin tai siitä puuttuu tavutusmerkki. Tämä myös rajaa sen mahdollisuuden pois, että käyttäjä kirjoittaa useamman tavutusmerkin. (b) Jos käyttäjän syöttämän sanan ensimmäinen merkki on tavutusmerkki, vaikka alkuperäisessä sanassa näin ei ollut, niin tavutusta ei hyväksytä, koska sanoja ei voi tavuttaa ennen ensimmäistä kirjainta. (c) Jos käyttäjän syöttämän sanan viimeinen merkki on tavutusmerkki, vaikka alkuperäisessä sanassa näin ei ollut, niin tavutusta ei hyväksytä, koska sanoja ei voi tavuttaa viimeisen kirjaimen jälkeen. (d) Ohjelma käy läpi käyttäjän syöttämän sanan ja vertaa sitä alkuperäisen sanaan, merkki kerrallaan. Kummallakin sanalla on oma läpikävijänsä, jotka käyvät samaantahtiin läpi sanojen merkkejä. Jos havaitaan eroavaisuutta, niin ainut hyväksyttävä poikkeus merkeissä on tavutusmerkki. Tavutusmerkin kohdatessa käyttäjän syöttämän sanan läpikävijää siirretään yksi merkki eteenpäin, jotta sanojen merkit täsmäisivät jälleen. Tällä prosessilla käydään läpi koko alkuperäinen sana, jolloin myös tarkastetaan, että käyttäjän syöttämä sana on kirjoitettu oikein. Missä tahansa tavutuksen hylkäämisessä ohjelma pyytää käyttäjää syöttämään tavutuksen uudestaan ja prosessia jatketaan kunnes tavutus on hyväksytty. 9

10 3.2.4 Ohjelma pseudokoodina WHILE (alkuperäisessä tekstissä on rivejä jäljellä) DO merkkijono = merkkijono + + alkuperäisen tekstin seuraava rivi // Nyt avatun tiedoston teksti on järjestetty yhdeksi pitkäksi // merkkijonokokonaisuudeksi a = merkkijonon ensimmäinen merkki b = merkkijonon ensimmäinen merkki c = ensimmäinen paikka taulukossa WHILE (merkkijonoa on jäljellä) DO { IF (a == ) THEN { WHILE (toinen välilyönti on löytynyt) b = b:n seuraava merkki IF (b = ) THEN { toinen välilyönti on löytynyt sanat[c] = a:n ja b:n väliin jäävät merkit c = seuraava paikka taulukossa a = b:n seuraava merkki // Nyt sanat on eritelty merkkijonokokonaisuudesta c = taulukon ensimmäinen alkio d = taulukon ensimmäinen paikka WHILE (sanoja on jäljellä sanat[] taulukossa) DO { IF (sanat[c] sanassa on * merkki) THEN { poista * merkki sanasta uusikappale = ok IF (rivit[d] + sanat[c] on yli tulostusrivin koko, mutta sanat[c] ei ole yli 12 merkkiä pitkä) THEN d = seuraava paikka taulukossa ELSE IF (rivit[d] + sanat[c] on yli tulostusrivin koko ja sanat[c] on yli 12 merkkiä pitkä) THEN 10

11 tavuttaminen = ok IF (tavuttaminen = ok) THEN { anna käyttäjän kirjoittaa tavutus yhdellä - merkillä. Tarkasta, että tavutus on hyväksyttävä rivit[d] = rivit[d] + sanat[c] merkit tavutusmerkin kohdalle d = seuraava paikka rivit[d] = sanat[c] tavutusmerkin jälkeiset merkit ELSE rivit[d] = rivit[d] + sanat[c] + IF (uusikappale = ok) THEN { d = seuraava paikka taulukossa rivit[d] = kappaleen alkutyhjän verran välilyöntejä c = taulukon seuraava paikka 3.2.5 Kuva Lue.class luestringsyote() luointsyote() ohjelmintityo65.class main() String merkkijono LueTiedosto.class luetiedosto() Vector sanat Vector rivit Muokkaa.class teesana() muutasanoiksi() teeuusiteksti() Tulosta.class tulostateksti() teetavutus() 11

12 3.3 Luokat ja niiden metodit 3.3.1 public class ohjelmointityo65 Pääluokka on ohjelman sydän. 3.3.1.1 public static void main(string [] args) Pääluokka pyörittää ohjelmakokonaisuutta, kysyen aluksi käyttäjältä kaikki tarpeelliset syötteet ja kutsuen toisten luokkien metodeja tekstin muotoiluun ja tulostukseen. 3.3.2 public class Lue Luokka hoitelee kaikki tarvittavat syötetoiminpiteet. 3.3.2.1 public String luestringsyote() Metodin tarkoitus on lukea merkkijono syötteet käyttäjältä ja palauttaa ne. 3.3.2.1 public int lueintsyote(int min, int max) Metodin tarkoitus on lukea kokonaisluku syötteet käyttäjältä ja palauttaa ne. int min muuttujassa on sallittavan syötteen alaraja. int max muuttujassa on sallittavan syötteen yläraja. 3.3.3 public class LueTiedosto Luokka hoitaa tiedoston avaamisen ja lukemisen. 3.3.3.1 static String luetiedosto(string tiedosto) Metodin tarkoitus on avata ja lukea haluttu tiedosto, muodostaa siitä yksi iso merkkijonokokonaisuus ja palauttaa se. String tiedosto muuttujassa on käyttäjän syöttämä tiedostonnimi 3.3.4 public class Muokkaa Luokka hoitaa tekstin muotoiluun liittyvät toiminpiteet. 12

13 3.3.4.1 static Object teesana(string merkkijono, int alku, int loppu) Metodin tarkoitus on eritellä sanat annetusta tekstikokonaisuudesta omiksi kokonaisuuksiksi (erilliseksi sanoiksi) ja palauttaa ne. muutasanoiksi() metodi (katso alla) kutsuu tätä toiminpidettä. String merkkijono muuttujassa on luettu teksti yhtenä merkkijonokokonaisuutena. int alku muuttujassa on arvo mistä sanan muodostaminen alkaa. int loppu muuttujassa on arvo mihin sanan muodostaminen päättyy. 3.3.4.2 static Vector muutasanoiksi(string merkkijono) Metodin tarkoitus on käydä luetusta tiedostosta luotua merkkijonokokonaisuutta läpi ja etsiä kohtia, joista sanat alkavat ja loppuvat. Kun sanan alku ja loppu on löytynyt niin, metodi kutsuu teesana() metodia ja luo erillisen sanan. Tämän jälkeen luotu sana kokoelma palautetaan String merkkijono muuttujassa on luettu teksti yhtenä merkkijonokokonaisuutena. 3.3.4.3 public Vector luouusiteksti(vector sanat, int kappaleenalku, int tulostusrivinkoko) Metodin tarkoitus on luoda uusi tekstikokonaisuus eritellyistä sanoista ja palauttaa se. Vector sanat tietorakenteessa on luetun tiedoston merkkijono eritelty erillisiksi sanoiksi int kappaleenalku muuttujassa on käyttäjän syöttämän alkutyhän määrä. int tulostusrivinkoko muuttujassa on käyttäjän syöttämän tulostusrivin koko. 3.3.4.4 public String[] teetavutus(string sana, int rivinylitys) Metodin tarkoitus on suorittaa sanan tavutus tarpeen tullessa ja palauttaa sana tavutettuna. String sana muuttujassa on sana, johon tavutus tulee suorittaa. int rivinylitys muuttujassa on kohta, mistä kohdin tavutettava sana ylitti tulostusrivin koon. 13

14 3.3.5 public class Tulosta Luokka hoitaa kaikki tarvittavat tulostustoiminpiteet. 3.3.5.1 public void tulostateksti(vector rivit) Metodin tarkoitus on tulostaa muotoiltu teksti. Vector rivit tietorakenteessa on uudelleen muotoiltu tekstikokonaisuus riveittäin. 3.4 Muutosohjeet 3.4.1 Tiedoston nimi: Jos avattavan tiedostontyyppiä halutaan muuttaa, niin se onnistuu asettamalla haluamansa loppupääte LueTiedosto.java lähdekoodin riville 28, nykyisten.txt tilalle. Esimerkiksi jos loppupääte halutaan olevan.doc niin koodin riville 28 tulee tehdä seuraavanlainen muutos: FileReader syotetiedosto = new FileReader((tiedosto + ".doc")); 3.4.2 Tulostusrivin koko: Jos tulostusrivin minimi ja maksimi raja-arvoja tahdotaan muuttaa, niin se onnistuu asettamalla haluamansa arvot ohjelmointityo65.java lähdekoodin riville 40, nykyisten 30 ja 75 tilalle. Esimerkiksi jos raja-arvot halutaan muuttaa 10-100, niin koodin riville 40 tulee tehdä seuraavanlainen muutos: int tulostusrivinkoko = lue.lueintsyote(10, 100); 3.4.3 Kappaleen Alkutyhjän määrä: Jos kappaleen alkutyhjän minimi ja maksimi raja-arvoja tahdotaan muuttaa, niin se onnistuu asettamalla haluamansa arvot ohjelmointityo65.java lähdekoodin riville 46, nykyisten 1 ja 5 tilalle. Esimerkiksi jos raja-arvot halutaan muuttaa 5-10, niin koodin riville 46 tulee tehdä seuraavanlainen muutos: int kappaleenalku = lue.lueintsyote(5, 10); 14

15 4 Testaus Testattava tekstitiedosto on testi.txt, jonka sisältö on seuraavanlainen: testi.txt 1 10 20 30 40 50 60 70 75 80 Tama on ohjelmointityo 65:n testi tekstitiedosto. * Taman avulla testataan toimiiko ohjelma oikein. Seuraavat sanat eivat liity toisiinsa. Apina, banaani, persikkalikoori, APPELSIINIMIES, elamankavija!? Rehtimies........ oikukkaita valilyonteja,, teesanatoikein(), olion-korsi tai Ollakko vai ei *ko olla, kas siina * vasta pulma. LOPPU. Testisanasto on taysin huonolla inspiraatiolla keksittya, mutta niiden tarkoitus on loytyy mahdollisimman paljon erilaisia tilanteinta, mita ohjelma saa vastaansa. Tekstitiedostoa käytetään testaamiseen koko testaamisen ajan, ellei toisin mainita. 4.1 Ohjelman kysyessä anna luettavan tiedoston nimeä, jos antaa Testin tarkoitus: Odotettu tulos: Saatu tulos: nimen, joka on kirjoitettu isolla, vaikka tiedoston nimessä on Ohjelma hyväksyy syötteen mukana pieniä kirjaimia nimen, joka on kirjoitettu pienellä, vaikka tiedoston nimessä on Ohjelma hyväksyy syötteen mukana isoja kirjaimia nimen, jossa on loppupääte mukana Ohjelma ei hyväksy syötettä, ilmoittaa siitä käyttäjälle ja ohjelma sulkeutuu. nimen, joka ei ole.txt päätteellinen Ohjelma ei hyväksy syötettä, ilmoittaa siitä käyttäjälle ja ohjelma sulkeutuu. 4.2 Ohjelman kysyessä anna tulosterivin koko (30-75), jos antaa Testin tarkoitus: Odotettu tulos: Saatu tulos: kokonaisluvun, joka on pienempi kuin 30. Ohjelma ei hyväksy syötettä ja pyytää käyttäjää antamaan syötteen uudelleen kokonaisluvun, joka on suurempi kuin 75. Ohjelma ei hyväksy syötettä ja pyytää käyttäjää antamaan syötteen uudelleen desimaaliluvun sallittujen arvojen Ohjelma ei hyväksy syötettä ja 15

16 sisältä. tekstisyötteen kokonaisluvun sallittujen arvojen sisältä pyytää käyttäjää antamaan syötteen uudelleen Ohjelma ei hyväksy syötettä ja pyytää käyttäjää antamaan syötteen uudelleen Ohjelma hyväksyy syötteen ja prosessi jatkuu normaalisti 4.3 Ohjelman kysyessä anna kappaleen alkutyhjan maara (1-5), jos antaa Testin tarkoitus: Odotettu tulos: Saatu tulos: kokonaisluvun, joka on pienempi kuin 1. Ohjelma ei hyväksy syötettä ja pyytää käyttäjää antamaan syötteen uudelleen kokonaisluvun, joka on suurempi kuin 5. Ohjelma ei hyväksy syötettä ja pyytää käyttäjää antamaan syötteen uudelleen desimaaliluvun sallittujen arvojen sisältä. Ohjelma ei hyväksy syötettä ja pyytää käyttäjää antamaan syötteen uudelleen tekstisyötteen Ohjelma ei hyväksy syötettä ja pyytää käyttäjää antamaan syötteen uudelleen kokonaisluvun sallittujen arvojen sisältä Ohjelma hyväksyy syötteen ja prosessi jatkuu normaalisti 4.4 Tavuttaminen. Jos antaa ohjelman kysyessä syötteen, joka on Testin tarkoitus: Odotettu tulos: Saatu tulos: kirjoitettu erikokoisilla kirjaimilla kuin alkuperäinen sana on, ilman Ohjelma ei hyväksy syötettä, vaan ilmoittaa siitä käyttäjälle ja pyytää tavutusmerkkiä uutta syötettä kirjoitettu erikokoisilla kirjaimilla kuin alkuperäinen sana on, Ohjelma ei hyväksy syötettä, vaan ilmoittaa siitä käyttäjälle ja pyytää tavutusmerkin kanssa. uutta syötettä kirjoitettu täysin samankokoisin kirjaimin kuin alkuperäisessä Ohjelma ei hyväksy syötettä, vaan ilmoittaa siitä käyttäjälle ja pyytää sanassa, ilman tavutusmerkkiä. uutta syötettä kirjoitettu täysin samankokoisin kirjaimin kuin alkuperäisessä Ohjelma ei hyväksy syötettä, vaan ilmoittaa siitä käyttäjälle ja pyytää 16

17 sanassa, ja jossa tavutusmerkki on viimeinen kirjain kirjoitettu täysin samankokoisin kirjaimin kuin alkuperäisessä sanassa, ja jossa tavutusmerkki on ensimmäinen kirjain kirjoitettu täysin samankokoisin kirjaimin kuin alkuperäisessä sanassa, ja jossa useampi kuin yksi tavutusmerkki. kirjoitettu täysin samankokoisin kirjaimin kuin alkuperäisessä sanassa, ja jossa on yksi tavutusmerkki muualla kuin alussa tai lopussa. kirjoitettu täysin samankokoisin kirjaimin kuin alkuperäisessä sanassa, ja jossa on yksi tavutusmerkki, ja se on tulostusrivin ylittävän kohtaa aikaisemmin. kirjoitettu täysin samankokoisin kirjaimin kuin alkuperäisessä sanassa, ja jossa on yksi tavutusmerkki, ja se on tulostusrivin ylittävällä kohdalla tai sen jälkeen. uutta syötettä Ohjelma ei hyväksy syötettä, vaan ilmoittaa siitä käyttäjälle ja pyytää uutta syötettä Ohjelma ei hyväksy syötettä, vaan ilmoittaa siitä käyttäjälle ja pyytää uutta syötettä Ohjelma hyväksyy syötteen ja prosessi jatkuu normaalisti Sana tavutetaan käyttäjän määrittämästä kohdasta. Tavutuksen ensimmäinen puolisko (ennen tavutusmerkkiä) on vanhalla rivillä tavutusmerkin kera ja toinen puolisko (tavutusmerkin jälkeinen) on uudella rivillä. Sanaa ei tavuteta ollenkaan, vaan se kirjoitetaan suoraan uudelle riville kokonaisuutenaan. 4.5 Tekstin muotoilu. Yllamainittua testi tekstitiedostoa (testi.txt) käyttäen tarkistan, että muotoilu on tapahtunut oikein. 4.5.1 Läpiajo testaukset 1. Anna luettavan tiedoston nimi: testi Anna tulosterivin koko (30-75): 30 Anna kappaleen alkutyhjien maara (1-5): 5 Tulostusrivin tila loppui kesken kohdassa ^ Tavuta sana yhdesta kohtaa: persikkalikoori ^ per-sikkalikoori 17

18 Tulostusrivin tila loppui kesken kohdassa ^ Tavuta sana yhdesta kohtaa: APPELSIINIMIES ^ APPEL-SIINIMIES Tulostusrivin tila loppui kesken kohdassa ^ Tavuta sana yhdesta kohtaa: mahdollisimman ^ mahdol-lisimman 1 5 10 20 30 40 50 60 70 75 80 Tama on ohjelmointityo 65:n testi tekstitiedosto. Taman avulla testataan toimiiko ohjelma oikein. Seuraavat sanat eivat liity toisiinsa. Apina, banaani, persikkalikoori, APPEL- SIINIMIES, elamankavija!? Rehtimies........ oikukkaita valilyonteja,, teesanatoikein(), olion-korsi tai Ollakko vai eiko olla, kas siina vasta pulma. LOPPU. Testisanasto on taysin huonolla inspiraatiolla keksittya, mutta niiden tarkoitus on loytyy mahdollisimman paljon erilaisia tilanteinta, mita ohjelma saa vastaansa. Läpiajo testaukset 2. Anna luettavan tiedoston nimi: testi Anna tulosterivin koko (30-75): 45 Anna kappaleen alkutyhjien maara (1-5): 3 Tulostusrivin tila loppui kesken kohdassa ^ Tavuta sana yhdesta kohtaa: tekstitiedosto ^ tekstitiedo-sto Tulostusrivin tila loppui kesken kohdassa ^ Tavuta sana yhdesta kohtaa: valilyonteja ^ vali-lyonteja Tulostusrivin tila loppui kesken kohdassa ^ Tavuta sana yhdesta kohtaa: mahdollisimman ^ mahdol-lisimman 1 3 5 10 20 30 40 45 50 60 70 75 80 Tama on ohjelmointityo 65:n testi tekstitiedosto. Taman avulla testataan toimiiko ohjelma oikein. Seuraavat sanat eivat liity toisiinsa. Apina, banaani, persikkalikoori, APPELSIINIMIES, elamankavija!? Rehtimies........ oikukkaita valilyonteja,, teesanatoikein(), olion-korsi tai 18

19 Ollakko vai eiko olla, kas siina vasta pulma. LOPPU. Testisanasto on taysin huonolla inspiraatiolla keksittya, mutta niiden tarkoitus on loytyy mahdollisimman paljon erilaisia tilanteinta, mita ohjelma saa vastaansa. Läpiajo testaukset 3. Anna luettavan tiedoston nimi: testi Anna tulosterivin koko (30-75): 75 Anna kappaleen alkutyhjien maara (1-5): 4 Tulostusrivin tila loppui kesken kohdassa ^ Tavuta sana yhdesta kohtaa: elamankavija ^ ela-mankavija Tulostusrivin tila loppui kesken kohdassa ^ Tavuta sana yhdesta kohtaa: teesanatoikein() ^ tee-sanatoikein() 1 4 10 20 30 40 45 50 60 70 75 80 Tama on ohjelmointityo 65:n testi tekstitiedosto. Taman avulla testataan toimiiko ohjelma oikein. Seuraavat sanat eivat liity toisiinsa. Apina, banaani, persikkalikoori, APPELSIINIMIES, elamankavija!? Rehtimies........ oikukkaita valilyonteja,, tee- SanatOikein(), olion-korsi tai Ollakko vai eiko olla, kas siina vasta pulma. LOPPU. Testisanasto on taysin huonolla inspiraatiolla keksittya, mutta niiden tarkoitus on loytyy mahdollisimman paljon erilaisia tilanteinta, mita ohjelma saa vastaansa. Läpiajo testaukset 4. Anna luettavan tiedoston nimi: TESTI Anna tulosterivin koko (30-75): 62 Anna kappaleen alkutyhjien maara (1-5): 1 Tulostusrivin tila loppui kesken kohdassa ^ Tavuta sana yhdesta kohtaa: inspiraatiolla ^ inspiraatiol-la Tulostusrivin tila loppui kesken kohdassa ^ Tavuta sana yhdesta kohtaa: mahdollisimman ^ mah-dollisimman 1 5 10 20 30 40 45 50 60 62 70 75 80 Tama on ohjelmointityo 65:n testi tekstitiedosto. Taman avulla testataan toimiiko ohjelma oikein. Seuraavat sanat eivat liity toisiinsa. Apina, banaani, persikkalikoori, APPELSIINIMIES, elamankavija!? Rehtimies........ oikukkaita valilyonteja,, teesanatoikein(), olion-korsi tai Ollakko vai eiko olla, kas siina vasta pulma. LOPPU. Testisanasto on taysin huonolla inspiraatiolla keksittya, mutta niiden tarkoitus on loytyy mahdollisimman paljon erilaisia tilanteinta, mita ohjelma saa vastaansa. 19

20 Läpiajo testaukset 5. Anna luettavan tiedoston nimi: TeSti Anna tulosterivin koko (30-75): 36 Anna kappaleen alkutyhjien maara (1-5): 2 Tulostusrivin tila loppui kesken kohdassa ^ Tavuta sana yhdesta kohtaa: tekstitiedosto ^ tekstitie-dosto Tulostusrivin tila loppui kesken kohdassa ^ Tavuta sana yhdesta kohtaa: APPELSIINIMIES ^ APPELSI-INIMIES Tulostusrivin tila loppui kesken kohdassa ^ Tavuta sana yhdesta kohtaa: valilyonteja ^ va-lilyonteja 1 2 5 10 20 30 36 40 45 50 60 70 75 80 Tama on ohjelmointityo 65:n testi tekstitiedosto. Taman avulla testataan toimiiko ohjelma oikein. Seuraavat sanat eivat liity toisiinsa. Apina, banaani, persikkalikoori, APPELSI- INIMIES, elamankavija!? Rehtimies........ oikukkaita valilyonteja,, teesanatoikein(), olion-korsi tai Ollakko vai eiko olla, kas siina vasta pulma. LOPPU. Testisanasto on taysin huonolla inspiraatiolla keksittya, mutta niiden tarkoitus on loytyy mahdollisimman paljon erilaisia tilanteinta, mita ohjelma saa vastaansa. 20

1 Liite 3 Ohjelmalistaus Ohjelmointityö 65 Aki Heikkinen import java.util.vector; /** * Class ohjelmointityo65 * @version 1.1.0 05 kesäkuu 2007 * Ohjelmointityo 65 paaohjelma luokka, jonka alla koko ohjelmaa pyoritetaan. * @author Aki Heikkinen */ public class ohjelmointityo65 { /** * main() */ public static void main(string [] args) { Lue lue = new Lue(); Muokkaa muokkaa = new Muokkaa(); Tulosta tulosta = new Tulosta(); LueTiedosto luetiedosto = new LueTiedosto(); // Ohjelma kysyy kayttajalta luettavan tekstitiedoston nimea. System.out.print("Anna luettavan tiedoston nimi: "); String tiedostonnimi = lue.luestringsyote(); String merkkijono = new String(lueTiedosto.lueTiedosto(tiedostonNimi)); // Jos tekstitiedostoa ei löytynyt tai se on tyhjä // ohjelma suljetaan. if(merkkijono.length() == 0) { System.out.println(" Ohjelma suljetaan."); System.exit(0); // Tulostusrivin koko kysytaan kayttajalta, joka saa olla // minimissaan 30 ja maksimissaan 75 merkkia. System.out.print("Anna tulosterivin koko (30-75): "); int tulostusrivinkoko = lue.lueintsyote(30, 75); System.out.print("Anna kappaleen alkutyhjien maara (1-5): "); // Kappaleen alkutyhjan kysyminen kayttajalta, joka saa olla // minimissaan 1 ja maksimissaan 5 valilyontia. int kappaleenalku = lue.lueintsyote(1, 5); // Muuttaa luetun merkkijonokokonaisuuden sanoiksi. Vector sanat = muokkaa.muutasanoiksi(merkkijono); // Muokkaa sanojen kokonaisuuden uuteen muotoon. Vector rivit = muokkaa.luouusiteksti(sanat, kappaleenalku, tulostusrivinkoko); // Tulostaa muokatun tekstin. tulosta.tulostateksti(rivit); // main() // ohjelmointityo65

2 import java.io.bufferedreader; import java.io.*; /** * Class Lue * @version 1.0.0 05 kesäkuu 2007 * Luokkaa kaytetaan syotteiden vastaanottamiseen kayttajalta. * @author Aki Heikkinen */ public class Lue { /** * luestringsyote() * Luetaan merkkijono syote kayttajalta käyttäen BufferedReader ja * InputStreamReader luokkia. * @return String syotetty merkkijono. */ public String luestringsyote() { String arvo = ""; boolean toimii; BufferedReader syote = new BufferedReader(new InputStreamReader(System.in)); do { try { arvo = syote.readline(); toimii = true; catch (Exception e) { System.out.println("Virheellinen syote, anna uusi!"); toimii = false; while(!toimii); return arvo; // luestringsyote() /** * lueintsyote() * Luetaan kokonaislukusyote kayttajalta, jonka tulee olla parametreina * annettujen minimin ja maksimi arvojen sisalla. * @param int min, int max suotten rajoittavat minimi ja maksimi arvot. * @return int Syotteena luettu kokonaisluku. */ public int lueintsyote(int min, int max) { int arvo = 0; boolean toimii; BufferedReader syote = new BufferedReader(new InputStreamReader(System.in)); do { try { arvo = Integer.parseInt(syote.readLine()); if(arvo < min arvo > max) { toimii = false; System.out.print("Virheellinen syote, anna uusi (" + min + "-" + max + "): "); else toimii = true;

3 // Lue catch (Exception e) { System.out.print("Virheellinen syote, anna uusi (" + min + "-" + max + "): "); toimii = false; while(!toimii); return arvo; // lueintsyote() import java.io.bufferedreader; import java.io.filereader; import java.io.*; /** * Class LueTiedosto * @version 1.2.0 05 kesäkuu 2007 * Luokan tarkoitus on tarkistaa onko haluttu tiedosto olemassa tai voiko sen lukea. * @author Aki Heikkinen */ public class LueTiedosto { /** * luetiedosto() * Tarkastaa onko tiedosto olemassa, eikä se ole tyhjä, jos näin on, niin * luo siita yhden merkkijonon. * @param String tiedosto avattavan tiedoston nimi. * @return String Avatun ja luetun tiedoston koko sisalto merkkijonona. */ static String luetiedosto(string tiedosto) { // LueTiedosto String teksti = ""; try { // Tiedoston on oltava.txt loppuinen FileReader syotetiedosto = new FileReader((tiedosto + ".txt")); BufferedReader tekstitiedosto = new BufferedReader(syotetiedosto); // Lukee tiedoston sisallon ja luo sen // koko sisallosta yhden pitkan merkkijonon while(tekstitiedosto.ready()) teksti = teksti +" "+ tekstitiedosto.readline(); // Jos tiedosto on löytynyt, mutta se on tyhjä if(teksti == "") System.out.print("Tiedosto on tyhjä!"); catch(ioexception e) { System.out.print("Tiedostoa ei loytynyt!"); teksti = ""; return teksti; // luetiedosto()

4 import java.util.vector; /** * Class Tulosta * @version 1.2.0 05 kesäkuu 2007 * Luokka suorittaa tulostustoiminpiteet * @author Aki Heikkinen */ public class Tulosta { /** * tulostateksti() * Tulostaa parametreina saadun Vector luokan sisallon. * @param Vector rivit tulostettava teksti. */ public void tulostateksti(vector rivit) { int f = 0; boolean tulostarivi = true; System.out.println(); // Tulostaminen lopetataan, kun vektorissa ei ole enaa alkioita. while(tulostarivi) { if(f == rivit.size()) tulostarivi = false; else { // Itse tulostaminen. System.out.println(rivit.get(f).toString()); f++; // tulostateksti() // Tulosta import java.io.bufferedreader; import java.io.*; import java.util.vector; /** * Class Muokkaa * @version 1.4.2 05 kesäkuu 2007 * Luokan tarkoitus on suorittaa tekstinmuokkausta. * @author Aki Heikkinen */ public class Muokkaa { /** * teesana() * Luekee merkkijonosta irrallisia sanoja ja palauttaa ne. * @param String merkkijono, int alku, int loppu. Merkkijono on koko teksti josta * muodotetaan sanat, alku ja loppu ovat merkkijonon kohdat joista sanan muodostus * aloitetaan ja lopetataan. * @return Object */ static Object teesana(string merkkijono, int alku, int loppu) { String sana = "";

5 Object palautus = new Object(); for(int q = alku; q < loppu; q++) // Tekee sanan merkkijonosta aloittamalla merkkijonon // 'alku' kohdasta ja lopettamalla 'loppu' kohtaan. sana = sana + merkkijono.charat(q); palautus = sana; return palautus; // teesana() /** * muutasanoiksi() * Luo merkkijonosta helpommin hallittavan kokonaisuuden asettamalla * jokaisen sanan omaan vektori luokan alkioon. * @param String merkkijono muokattava teksti. * @return Vector sanakokoelma vektori alkioina. */ static Vector muutasanoiksi(string merkkijono) { // 'i' kuvaa sanan alkua ja 'j' sanan loppua. int i = 0, j; boolean jatkuu; Object objekti = new Object(); Vector palautus = new Vector(1,1); // Suorittaa kunnes merkkijono on kayty lapi. while(i < merkkijono.length()) { jatkuu = true; // Ensimmainen valiloynnin, eli sanan alun tarkastaminen. if(merkkijono.charat(i) == ' ') { j = i+1; // Suorittaa kunnes toinen valilyonti, eli sanan loppu // tai merkkijonon loppu on loytynyt. while(jatkuu) { // Tarkastaa onko merkkijono loppu. if (j == merkkijono.length()) { palautus.add(teesana(merkkijono, (i+1), j)); jatkuu = false; i = j; // Toisen valilyonnin tarkastaminen. else if (merkkijono.charat(j) == ' ') { else i++; else palautus.add(teesana(merkkijono, (i+1), j)); jatkuu = false; i = j; j++;

6 return palautus; // muutasanoiksi() /** * luouusiteksti() * Luo vektorialkioista uuden tekstikokonaisuuden annettujen parametrien * mukaan. Uusi teksti luodaan riveittain ja jokainen luotu rivi tallennetaan * vektori luokan alkioon. * @param Vector sanat, int kappaleenalku, int tulostusrivinkoko. Sanat ovat on * tekstikokonaisuus vektorialkioina; yksi sana per alkio. KappaleenAlku on * kappaleen alkutyhjän määrä välilyönteinä. * TulostusrivinKoko on tulostusrivin koko merkkeinä. * @return Vector uudeksi kokonaisuudeksi muotattu tekstikokonaisuus, jonka kukin * rivi on oma alkionsa. */ public Vector luouusiteksti(vector sanat, int kappaleenalku, int tulostusrivinkoko) { int a = 0, e = 0, sananen; String tavutus[]; String rivi ="", uusisana; boolean kappaleenjako = false, jatkuu=true; Object objekti = new Object(); Vector palautus = new Vector(1,1); while(jatkuu) { if(a == sanat.size()) { jatkuu = false; objekti = rivi; palautus.add(objekti); else { // kasiteltavan sanan merkkipituus. sananen = sanat.get(a).tostring().length(); // Tarkastaa onko sanassa kappaleenjako * -merkkia. for(int b=0; b < sanat.get(a).tostring().length(); b++) if(sanat.get(a).tostring().charat(b) == ' ' && sanat.get(a).tostring().charat((b+1)) == '*') { kappaleenjako = true; uusisana = ""; // Kappaleen jakomerkki poistetaan sanasta. for(int d =0; d < (sananen); d++) if(d == b d == (b+1)); else uusisana = uusisana + sanat.get(a).tostring().charat(d); objekti = uusisana; sanat.set(a, objekti); // Jos tulostusrivinkoko ylitetaan. if((rivi.length() + sananen) > tulostusrivinkoko) {

7 // Jos sana on yli 12 merkkia pitka ja se ylittaa rivin // vahintaan 2 merkilla, niin se tavutetaan. if(sananen > 12 && sananen - (rivi.length() + sananen tulostusrivinkoko) > 1) { tavutus = teetavutus(sanat.get(a).tostring(), (rivi.length() + sananen - tulostusrivinkoko)); // Tavutetun sanan lisaaminen valmiiseen teksti vektoriin. rivi = rivi + tavutus[0]; objekti = rivi; palautus.add(objekti); // Tavutuksen toinen puolisko on uuden rivin alussa. rivi = tavutus[1] + " "; // Jos rivinylittava sana ei tayta yllamainittuja kriteereja // se asetetaan suoraan uuden rivin alkuun. else { objekti = rivi; palautus.add(objekti); rivi = sanat.get(a).tostring() + " "; // Kun tulostusrivia ei ole viela ylitetty, rivin luomista jatketaan. else rivi = rivi + sanat.get(a).tostring() + " "; // Jos kappaleen jakomerkki on loytetty tekstista, niin // suoritetaan kappaleenjako. if(kappaleenjako) { objekti = rivi; palautus.add(objekti); rivi = ""; for(int i=0; i < kappaleenalku; i++) rivi = rivi + " "; kappaleenjako = false; a++; return palautus; // luouusiteksti() /** * teetavutus() * Sanojen tavutuksen suorittaminen. * @param String sana, int rivinylitys. Sana on tavutettava sana ja rivinylitys on * kuinka monen merkin kohdalla sana ylitti tulostusrivin koon. * @return String[] tavutettu sana kaksi alkioisena taulukkona, ensimmäisessä * alkiossa on tavutusmerkkiä edeltävä osa ja toisessa alkiossa on jälkimmäinen osa */

8 public String[] teetavutus(string sana, int rivinylitys) { boolean toimii = false, ok, virheeton; String tavutus[] = new String[2]; tavutus[0]= ""; tavutus[1]= ""; BufferedReader sisaan = new BufferedReader(new InputStreamReader(System.in)); String syote = "", loppuosa = "", temp = ""; int b, c, d=0, mones=0, raja = (sana.length() - rivinylitys); // Jos tavutetussa sanassa on erikoismerkkeja ne erotetaan sanasta. // Ohjelma olettaa, ettei kyseisia merkkeja ole sanojen valissa tai alussa, // vaan etta luettava teksti on aidinkielellisesti kunnossa. for(int u = 0; u < sana.length(); u++) { if(sana.charat(u) == '.') loppuosa = loppuosa + "."; if(sana.charat(u) == ',') loppuosa = loppuosa + ","; if(sana.charat(u) == ':') loppuosa = loppuosa + ":"; if(sana.charat(u) == ';') loppuosa = loppuosa + ";"; if(sana.charat(u) == '"') loppuosa = loppuosa + "\""; if(sana.charat(u) == '!') loppuosa = loppuosa + "!"; if(sana.charat(u) == '?') loppuosa = loppuosa + "?"; if(sana.charat(u) == '\'') loppuosa = loppuosa + "\'"; // Erikoismerkkien karsiminen sanasta for(int y = 0; y < (sana.length() - loppuosa.length()); y++) temp = temp + sana.charat(y); sana = temp; System.out.println(); System.out.println("Tulostusrivin tila loppui kesken kohdassa ^ Tavuta sana yhdesta kohtaa: "); // Itse tavutuksen suorittaminen kaydaan lapi tavuttamista // kunnes se on hyvaksytty. while(!toimii) { b = 0; c = 0; ok = true; toimii = true; // Esittaa kayttajalle mista kohtaa sana ylittaa tulostusrivin. System.out.println(sana); for(int i=0; i < raja; i++) System.out.print(" "); System.out.println("^"); // Käyttäjän syöttämän tavutuksen vastaanottaminen. do {

9 try { syote = sisaan.readline(); virheeton = true; catch (Exception e) { System.out.println("Virheellinen syote, anna uusi!"); virheeton = false; while(!virheeton); // Tarkastaako onko kayttajan antama tavutus hyvaksyttava. while(ok) { // Tavutetun sanan tulee olla tavutusmerkin kanssa yhden merkin // pidempi kuin alkuperainen sana. if(syote.length()!= (sana.length()+1)) { ok = false; toimii = false; // Jos tavutus on suoritettu ennen ensimmäistä kirjainta else if(syote.charat(0)!= sana.charat(0) && syote.charat(0) == '-') { toimii = false; ok = false; // Jos tavutus on suoritettu viimeisen kirjaimen jälkeen else if(syote.charat(syote.length()-1)!= sana.charat(sana.length()-1) && syote.charat(syote.length()-1) == '-') { toimii = false; ok = false; // Jos sana on hiukan muuttunut tarkastetaan johtuuko se // tavutusmerkista, joka on ainut hyvaksyttava syy. else { if(syote.charat(b)!= sana.charat(c)) { if(syote.charat(b) == '-') { mones = b; b++; //...muuten sana ei ole kevollinen vaan se on muuttunut. else { toimii = false; ok = false; System.out.println(); else { b++; c++;

10 // Tarkastuskierroksen lopettaminen. if(c == sana.length()) ok = false; // Virheilmoitus, jos tavutus ei ole kelvollinen. if(!toimii) { System.out.println(); System.out.println("Virhe! Olet kirjoittanut sanan vaarin, yrita uudelleen:"); // Jos tavutettu sana on tavutettu tulostusrivin ylittaneeseen osaan, // niin koko sana asetetaan uudelle riville. if(mones >= raja) { d++; for(int q=0; q < syote.length(); q++) { if(syote.charat(q)!= '-') tavutus[d] = tavutus[d] + syote.charat(q); //...Muuten tavutettu sana jaetaan kahdelle riville tavutuskohdasta. else { for(int q=0; q < syote.length(); q++) { tavutus[d] = tavutus[d] + syote.charat(q); if(syote.charat(q) == '-') d++; // Tavutuksen toiseen puoliskoon liitetään myös loppuosa tavutus[1] = tavutus[1] + loppuosa; return tavutus; // teetavutus() // Muokkaa