(Muutettu viimeksi 19.9.2011, sivu perustettu 5.9.2011.)
Nämä harjoitukset liittyvät oppimateriaalin lukuihin 1 Algoritmeja: 24-34.
Kaikki harjoitustehtävät on syytä tehdä. Jotkin tehtävät on merkitty keltaisella värillä. Ne ovat ehkä hieman muita haastavampia. Ilman niitäkin harjoituksista voi saada maksimipisteet, mutta ne lasketaan silti mukaan harjoituspisteitä määrättäessä – ne voivat siis korvata joitakin haasteettomampia tehtäviä tms. Mutta ennen kaikkea noista keltaisista tehtävistä sitä vasta oppiikin!
Huom:
// 3. harjoitukset, tehtävä 1.3, Oili Opiskelija
Tässä harjoitellaan oppimateriaalin kohtaa 1 Algoritmeja: aliluvut 24-26.
Laadi tämän kohdan ohjelmat sellaisiksi, että ne toimivat kaiken kokoisilla taulukoilla. Kokeile siis muitakin kuin esimerkkitaulukkoja. Vaihda tässä vaiheessa vain taulukon määrittelyä ohjelmassasi. Arvojen lukeminen taulukkoon aloitetaan vasta seuraavassa kohdassa. Tulosta tämän alikohdan ohjelmissa standarditulosvirtaan eli käytä System.out.println- ja System.out.print-operaatioita.
Tee ohjelma joka tulostaa taulukon ensimmäisen ja viimeisen alkion.
Jos taulukko on esimerkiksi
int[] taulukko = {5,11,3,84,2};
,
ohjelma tulostaa:
Ensimmäinen: 5 Viimeinen: 2
Jos taulukko on
int[] taulukko = {-1, 3, 2, 7};
,
ohjelma tulostaa:
Ensimmäinen: -1 Viimeinen: 7
Tee ohjelma joka tulostaa taulukon keskimmäisen alkion. Mikä on keskimmäinen, jos alkioita on parillinen määrä? Voit päättää asian itse.
Tee ohjelma, joka tulostaa taulukon alkiot ja alkoiden summan.
Jos taulukko on esimerkiksi
int[] taulukko = {5,11,3,84,2};
,
ohjelma tulostaa:
Taulukon alkiot: 5 11 3 84 2 Summa: 105
Jos taulukko on
int[] taulukko = {-1, 3, 2, 7};
,
ohjelma tulostaa:
-1 3 2 7 Summa: 11
Jos taulukko on esimerkiksi
int[] taulukko = {5,11,3,84,2};
,
ohjelma tulostaa:
Taulukon alkiot käänteisessä järjestyksessä: 2 84 3 11 5
Jos taulukko on
int[] taulukko = {-1, 3, 2, 7};
,
ohjelma tulostaa:
Taulukon alkiot käänteisessä järjestyksessä: 7 2 3 -1
Tulosta taulukon alkiot tyylikkäästi siten, että niiden väliin tulee pilkku ja välilyönti. Huomaa, että lopussa ei saa olla pilkkua; virkkeethän päättyvät pisteeseen.
Taulukon alkiot ovat 5, 11, 3, 84, 2.
Ohjelmassasi on taulukko, jossa on arvoja. Ohjelma kysyy
ponnahdusikkunan avulla
käyttäjältä lukua ja selvittää, onko luku taulukossa.
Suoritus esimerkkitaulukolla
int[] taulukko = {1, 53, 2, 3, 100};
Löytyy!
Tässäkin harjoitellaan oppimateriaalin kohtaa 1 Algoritmeja: aliluvut 24-26.
Lue ponnahdusikkunaa käyttäen taulukkoon
int[] luvut = new int[7]
seitsemän kokonaislukua ja tulosta luetut luvut
kauniisti standarditulosvirtaan:
Syötit luvut: 1, 32, 6, 8, 12, 17, 22.
Huom: Älä kirjoita seitsemään kertaan Pop.kysyInt! Sen sijaan käytä for-lausetta.
Ohjelmassasi on taulukko, jossa on arvoja. Ohjelma kysyy
käyttäjältä lukua ja jatkaa kyselyä niin kauan, kunnes käyttäjä
arvaa jonkin taulukossa olevan luvun. Suoritus esimerkkitaulukolla
int[] t = {1, 53, 2, 3, 100, 9, 53}
:
Yhdistä kahden edellisten tehtävien ratkaisut yksinkertaiseksi tietokonepeliksi: Ensin ohjelma pyytää käyttäjältä seitsemän kokonaislukua ja sijoittaa ne 7-alkioisen taulukon alkioiden arvoksi. Sen jälkeen (toinen) käyttäjä alkaa arvailla lukuja edellisen tehtävän tapaan.
Ohjelma keskustelee käyttäjien kanssa ponnahdusikkunoin.
Kehittelemällä edellisten tehtävien ideoita voit toteuttaa yksinkertaisen, mutta jo ihan oikean tietokonepelin: Ensin ohjelma pyytää syötettävien lukujen lukumäärän pelinjohtajalta ja sitten itse luvut. Sovitaan että tässä pelissä sallittuja ovat vain luvut 1–21, muut hylätään. Sama luku saa esiintyä useampaankin kertaan.
Tämän jälkeen pelaaja istuu koneen ääreen ja peli alkaa. Pelaaja yrittää arvata koneelle syötettyjä lukuja. Peli päättyy, kun pelaaja arvaa jonkin pelinjohtajan syöttämistä luvuista, ja tulos on tarvittujen arvauskertojen lukumäärä.
Pelinjohtaja:
Ja näin jatkuu, kunnes kaikki luvut on annettu:
Sovitaan että pelinjohtaja syötti luvut 11, 17, 6, 8, 12 ja 17.
Sitten on pelaajan vuoro.
Epäonnistunut arvaus:
Tyhmään arvaukseen vahvempi palaute:
Viimeinkin osuu:
Kun saat ohjelman muuten kuntoon, mieti miten käyttäjän Cancel- tai ylärastiklikkaukseen tulisi suhtautua. Jos jaksat, toteuta myös haluamasi suhtautumistavat.
Tässä harjoitellaan oppimateriaalin kohtaa 1 Algoritmeja: aliluvut 27-28.
Käytetään merkkijonotaulukkoa ja kokonaislukutaulukkoa rinta rinnan. Kurssimateriaalissa on esimerkki:
String[] henkilot = {"Matti", "Maija", "Pekka", "Liisa"}; int[] ika = { 29, 22, 19, 27};
Kirjoita pieni ohjelma, joka tässä tietorakenteessa kasvattaa jokaisen henkilön ikää yhdellä ja onnittelee jokaista, joka täyttää tasavuosia. Onnentoivotukset saavat siis Matti ja Pekka.
Jatketaan edellisen tehtävän hengessä. Tee ohjelma, joka kysyy ensin henkilöiden lukumäärän, sitten yksitellen jokaisen henkilön nimen ja iän. Ohjelman tehtävänä on tulostaa nimet ja iät standarditulosvirtaan. Syötteet luetaan ponnahdusikkunoin.
Jos ohjelmalle vaikkapa syötetään lukumääräksi 4 ja sitten nimet ja iät: Matti, 29, Maija, 22, Pekka, 19, Liisa 27, ohjelma tulostaa:
Matti on 29-vuotias. Maija on 22-vuotias. Pekka on 19-vuotias. Liisa on 27-vuotias.
Vihjeitä:
String[] henkilot = new String[henkLkm]; int[] ika = new int[henkLkm];
Täydennetään edellistä ohjelmaa todelliseksi palveluksi. Aluksi ohjelma edellisen tehtävän ohjelman tapaan kysyy henkilöiden lukumäärän, sitten yksitellen jokaisen henkilön nimen ja iän. Tämän jälkeen ohjelma tarjoaa palvelun henkilöiden iän selvittämiseksi: Käyttäjä antaa nimen ja ohjelma ilmoittaa kyseisen henkilön iän tai tiedon siitä, ettei kysyttyä henkilöä löydy.
Käytä ponnahdusikkunoita ja päätä itse, miten ohjelmalle ilmaistaan palvelun käytön lopettaminen.
Vihje ja virike:
Käytä tämän tehtäväsarjan toimittamiseen palautusautomaattia! Ohje sivun alussa.
Tässä harjoitellaan oppimateriaalin kohtaa 1 Algoritmeja: aliluvut 29-34. Lähdetään liikkeelle hyvin pienestä, mutta ei huolta, kyllä pian päästään pidemmälle.
Ohjelmoi parametriton metodi tahti1(), joka vain tulostaa yhden tähtimerkin (*) standarditulosvirtaan riviä vaihtamatta. Laadi myös pääohjelma, joka kutsuu tätä metodia.
Neuvo: Koko ohjelman rakenne on seuraavanlainen:
public class Tahti1 { // metodin määrittely: private static void tahti1() { // tänne tulee metodin vaativa toiminnallisuus // eli se yhden tähden tulostaminen ilman rivinvaihtoa } // pääohjelma public static void main(String[] args) { System.out.println("Tähtitesti"); tahti1(); // metodin kutsuja tahti1(); System.out.println("Moido!"); } }
Ohjelman tulostus:
Tähtitesti **Moido!
Ohjelmoi int-parametrinen metodi tahtiN(int kpl), joka tulostaa parametrin ilmaiseman määrän tähtiä (*) standarditulosvirtaan riviä vaihtamatta. Jos parametri on nolla tai negatiivinen, mitään ei tulosteta. Laadi myös pääohjelma, joka kutsuu tätä metodia.
Neuvo: Koko ohjelman rakenne on seuraavanlainen:
public class TahtiN { // metodin määrittely: private static void tahtiN(int kpl) { // tänne tulee metodin toiminnallisuus // eli tähtirivin tulostaminen ilman rivinvaihtoa } // pääohjelma public static void main(String[] args) { tahtiN(5); // metodin kutsu System.out.println("Ahaa!"); tahtiN(14); // metodin kutsu System.out.println("Moido!"); } }
Ohjelman tulostus:
*****Ahaa! **************Moido!
Ohjelmoi yksiparamertinen metodi tahditaTeksti(String teksti), joka tulostaa standarditulosvirtaan parametritekstin ympäröitynä tähtimerkein. Esimerkki alla. Käytä hyväksi edellä ohjelmoitua metodia tahtiN(int kpl). Merkkijonon merkkien lukumäärän saa ns. lenght()-aksessorilla: muuttuja.lenght().
Neuvo: Koko ohjelman rakenne on seuraavanlainen:
public class TahtiN { // metodien määrittelyt: private static void tahtiN(int kpl) { // tänne tulee metodin toiminnallisuus // eli tähtirivin tulostaminen ilman rivinvaihtoa } private static void tahditaTeksti(String teksti) { // tänne tulee metodin toiminnallisuus // täältä kutsutaan metodia tahtiN(int kpl) } // pääohjelma public static void main(String[] args) { tahditaTeksti("Tervetuloa!"); // pääohjelma siis kutsuu metodia tahditaTeksti("ABC"); // tahditaTeksti, joka puolestaan tahditaTeksti("Hei hei!"); // kutsuu metodia tahtiN } }
Ohjelman tulostus:
*************** * Tervetuloa! * *************** ******* * ABC * ******* ************ * Hei hei! * ************
Ohjelmoi yksiparamertinen metodi tahditaTekstit(String[] teksti), joka tulostaa standarditulosvirtaan parametrina saadun merkkijonotaulukon jokaisen merkkijonon ympäröitynä tähtimerkein. Esimerkki alla. Käytä hyväksi edellä ohjelmoituja metodeja tahtiN(int kpl) ja tahditaTeksti(String teksti).
Neuvo: Koko ohjelman rakenne on seuraavanlainen:
public class TahtiN { // metodien määrittelyt: private static void tahtiN(int kpl) { // tänne tulee metodin toiminnallisuus // eli tähtirivin tulostaminen ilman rivinvaihtoa } private static void tahditaTeksti(String teksti) { // tänne tulee metodin toiminnallisuus // täältä kutsutaan metodia tahtiN(int kpl) } private static void tahditaTekstit(String[] teksti) { // tänne tulee metodin toiminnallisuus // täältä kutsutaan metodia tahditaTeksti(String teksti) } // pääohjelma public static void main(String[] args) { String [] tekstit = {"Tervetuloa", "ABC", "Hei hei!"}; tahditaTekstit(tekstit); // pääohjelma siis kutsuu metodia // tahditaTekstit, joka puolestaan // kutsuu metodia tahditaTeksti, joka // kutsuu metodia tahtiN } }
Ohjelman tulostus:
*************** * Tervetuloa! * *************** ******* * ABC * ******* ************ * Hei hei! * ************
Ohjelmoi metodi
private static void jaonTulos(int eka, int toka)
,
joka tulostaa jakolaskun seuraavan esimerkin mukaisesti.
128 / 8 = 16.0 5 / 3 = 1.66666666666667
Laadi myös pääohjelma, joka esittelee metodin käyttöä.
Huom: (21.9.) Jos käytät tarkistusautomaattia, anna metodille nimeksi jakolasku. On nimittäin kuulemma helpompi kirjoittaa tämä viesti tänne kuin muuttaa automaattia. ;-)
Käytä tämän tehtäväsarjan toimittamiseen palautusautomaattia! Ohje sivun alussa.
Tässäkin harjoitellaan oppimateriaalin kohtaa 1 Algoritmeja: aliluvut 29-34.
Tee metodi private static double keha(...)
, joka palauttaa arvonaan
ympyrän kehän (piirin) pituuden. Säde annetaan double
-parametrina.
Piin mahdollisimman tarkan double-arvon saat kirjastosta: Math.PI
.
Niin, se kaava taisi olla "kaks'pii'är"...
Neuvo: Koko ohjelman rakenne olkoon seuraavanlainen:
public class PiiArToiseen { // metodin määrittely: private static double keha(double sade) { // täältä palautetaan laskettu arvo return-lauseella } // pääohjelma public static void main(String[] args) { double saatuSade = Pop.kysyDouble("Anna säde!"); double piiri = keha(saatuSade); // metodin kutsu System.out.println(piiri); saatuSade = Pop.kysyDouble("Anna säde!"); piiri = keha(saatuSade); // metodin kutsu System.out.println(piiri); }
Kun ohjelmalle syötetään luvut 20.0 ja 1.0, saadaan tulostus:
125.66370614359172 6.283185307179586
Ohjelmoi int-tyyppinen metodi vastaluku, joka laskee parametrina annetun kokonaisluvun vastaluvun. Tämä tarkoittaa, että positiivinen luku muuttuu negatiiviseksi ja päinvastoin.
Laadi myös pääohjelma, joka esittelee metodin käyttöä.
Ohjelmoi double-tyyppinen metodi kahdenKarvo, joka laskee kahden parametrina annetun liukuluvun keskiarvon.
Laadi myös pääohjelma, joka esittelee metodin käyttöä.
Ohjelmoi boolean-tyyppinen metodi onPariton, joka palauttaa arvon true, jos parametrina annettu kokonaisluku on pariton. Muuten metodi palauttaa arvon false.
Laadi myös pääohjelma, joka esittelee metodin käyttöä.
Huomaa että totuusarvoista metodia kutsutaan siellä, missä totuusarvoja muutenkin käytetään! Siis esimerkiksi if- tai while-lauseen ehdossa. Siis tähän tyyliin:
... int luku = ... ... if (onPariton(luku)) ... else ... while (onPariton(luku)) { ... }
Käytä tämän tehtäväsarjan toimittamiseen palautusautomaattia! Ohje sivun alussa.
Edelleen harjoitellaan oppimateriaalin kohtaa 1 Algoritmeja: aliluvut 29-34.
Ohjelmoidaan arvosanajakauman laskenta vaiheittain. Arvosanat ovat: 0, 1, 2, 3, 4 ja 5. Nolla tarkoittaa hylättyä.
Laadi metodi private static int[] arvosanaMaarat(), joka kysyy ponnahdusikkunan avulla opettajalta arvosanojen määrät yksi kerrallaan; ensin 0-arvosanojen lukumäärän, sitten 1-arvosanojen lukumäärän, jne.
Metodin tyyppi on siis int[], mikä tarkoittaa, että metodi itse luo arvosanojen lukumäärää varten 6-alkioisen int-taulukon, kyselee arvosanojen lukumäärät, asettaa ne taulukkoon ja lopuksi palauttaa tuon taulukon return-lauseella. Metodi siis näyttää tältä:
private static int[] arvosanaMaarat() { int[] arvMaarat = new int[6]; // kysele yksitellen arvosanojen lukumäärät ja vie ne taulukkoon return arvMaarat; }
Ohjelmoi myös itse luokka ja metodin käyttöä esittelevä pääohjelma tyyliin:
public class Arvosanajakauma { private static int[] arvosanaMaarat() { ... } // pääohjelma public static void main(String[] args) { int[] maarat; maarat = arvosanaMaarat(); // tulosta taulukot tiedot siististi } }
Jos opettaja vaikkapa syöttää lukumäärät 3, 3, 7, 2, 7, 10, ohjelma tulostaa tyyliin:
Arvosanat: 0: 3 kpl 1: 3 kpl 2: 7 kpl 3: 2 kpl 4: 7 kpl 5: 10 kpl
Täydennä luokkaa metodilla
private static double hyvPros(int[] arvosanajakauma)
,
joka saa parametrinaan arvosanajakaumataulukon ja joka laskee
hyväksyttyjen prosentuaalisen määrän kurssin kaikista osallistujista.
Täydennä ohjelman edellinen varsio seuraavan kaltaiseksi:
public class Arvosanajakauma { private static int[] arvosanaMaarat() { ... } private static double hyvPros(int[] arvosanajakauma) { // prosentin laskenta } // pääohjelma public static void main(String[] args) { int[] maarat; maarat = arvosanaMaarat(); // tulosta taulukot tiedot siististi System.out.println("Hyväksyttyjä " + hyvPros(maarat) + " % osallistujista"); } }
Edellisen kohdan esimerkissä tulostus voisi näyttää tältä:
Arvosanat: 0: 3 kpl 1: 3 kpl 2: 7 kpl 3: 2 kpl 4: 7 kpl 5: 10 kpl Hyväksyttyjä 90.625 % osallistujista
Täydennä luokka Arvosanajakauma tehtävän 4.2 metodilla private static void tahtiN(int kpl) ja viimeistele arvosanajakauman tulostusohjelma toimimaan seuraavaan tyyliin (sama esimerkkisyöte kuin edellä):
Arvosanat: 0: 3 kpl 1: 3 kpl 2: 7 kpl 3: 2 kpl 4: 7 kpl 5: 10 kpl Hyväksyttyjä 90.625 % osallistujista Arvosanajakauma: 5: ********** 4: ******* 3: ** 2: ******* 1: *** 0: ***
Huom: Älä ihmeessä rasita pääohjelmaa tähtirivien tulostamisen yksityiskohdilla! Laadi (ja nimeä!) tähän tarkoitukseen sopiva metodi, jota siis kutsutaan pääohjelmasta:
public class Arvosanajakauma { ... // pääohjelma public static void main(String[] args) { int[] maarat; maarat = arvosanaMaarat(); // tulosta taulukot tiedot siististi // tulosta hyväksyttyjen prosentti // tulosta arvosanajakauma } }
Toteuta metodi
private static int maaritteleArvosana(int pisteet)
,
jolle annetaan pisteet ja joka palauttaa pisteitä vastaavan arvosanan.
Metodi ei siis itse tulosta mitään, kunhan vain laskee.
Arvosana lasketaan seuraavasti:
30-34 pistettä: 1, 35-39: 2, 40-44: 3, 45-49: 4, 50-60 : 5 ja alle
30 pistettä on hylätty.
Muista miten arvosanan määräämisen logiikkaa harjoiteltiin jo ensimmäisen viikon tehtävässä 4.5!
Kehittele arvosanajakauman laskevasta ohjelmasta lopulta "ihan oikea" palvelu: Aluksi opettaja syöttää opiskelijoiden koepistemäärät. Kukin syötetty koepistemäärä muutetaan vastaavaksi arvosanaksi tehtävän 6.4 metodilla. Jokainen näin selvitetty arvosana kasvattaa yhdellä arvosanojen lukumääriä laskevan taulukon oikeaa alkiota.
Esimerkkisuoritus:
Ensin opettaja syöttää ponnahdusikkunan avulla opiskelijoiden pistemäärät (0-60) ohjelmalle, vaikkapa 44, 35, 17, 56, 7, ..., 54, -1.
Negatiivinen syöttöluku lopettaa pisteiden syötön.
Tämän jälkeen ohjelma tulostaa:
Arvosanajakauma: 5: ********** 4: ******* 3: ** 2: ******* 1: *** 0: *** Hyväksyttyjä 90.625 % osallistujista
Huomaa miten tässä monimutkainen ongelma ratkottiin pienempinä osaongelmina, jotka saatettiin yksi kerrallaan toimintakuntoon. Ohjelmointiongelmia kannattaa useimmiten lähestyä juuri tähän tyyliin!
Muista ohjelmoida tehtävää ratkoessasi tarpeen mukaan lisää omia metodeita: ei ole esimerkiksi mitään järkeä ohjelmoida pisteiden kyselyä suoraan pääohjelmaan!
Tämän viikon tehtävän 2.4 arvauspeli oli seuraavanlainen:
Ensin ohjelma pyytää syötettävien lukujen
lukumäärän pelinjohtajalta ja sitten itse luvut.
Sovitaan että tässä pelissä sallittuja ovat vain luvut 1–21,
muut hylätään. Sama luku saa esiintyä useampaankin kertaan.
Tämän jälkeen pelaaja istuu koneen ääreen ja peli alkaa.
Pelaaja yrittää arvata koneelle syötettyjä lukuja.
Peli päättyy, kun pelaaja arvaa jonkin pelinjohtajan syöttämistä
luvuista, ja tulos on tarvittujen arvauskertojen lukumäärä.
Arvauspeli on jo sen verran monimutkainen, että se toteuttaminen kaikkineen pääohjelmassa ei ole kovin viisasta eikä kaunista. Muokkaa siis ratkaisua siten, että ohjelmoit hyvä metodeita, joilla ohjelman toiminta saadaan selkeäksi.
Seuraavan kaltaiset metodit saattavat olla käyttökelpoisia:
private static onkoLukuTaulukossa(int luku, int[] taulukko)
private static int lueLukuValilta(int min, int max)
,
lukee käyttäjältä syötettä niin kauan kunnes syöte on annetulla välillä
käyttö: int luku = lueLukuValilta(alaraja, ylaraja)