Moido! :)
Kuinkahan mahdetaan toteuttaa Javassa sovellus, joka syöttää erilaisia tietoja ja tulostaa ne? Valintoina A)syötä henkilön nimi, B) syötä henkilön ikä, C) tulosta henkilön nimi ja ikä, sekä sitten L) lopeta ohjelma. Ohjelman tulisi ilmoittaa myös väärästä valinnasta. Arghhh :/
T
Runko on yksinkertainen: 0) Tee silmukka. 1) Lue syöte. 2) Tarkista syöte, tee eri vaihtoehdoille if-lauseet. 3) Tilanteissa A ja B lue lisää syötettä ja tallenna se oikeaan muuttujaan ja palaa silmukan alkuun (continue). 4) Tilanteessa C tulosta muuttujat ja palaa silmukan alkuun (continue). 5) L-syötteellä lopeta silmukka (break). 6) Jos mikään näistä ei toteutunut, tulosta virheilmoitus. Mikä kohta ohjelmassa tuottaa sinulle vaikeuksia? Mitä olet jo saanut aikaan?
Kuulostaa nyt siltä, että haluaisit saada valmiin ratkaisun Java-kurssin kotitehtävään mutta et ehkä ole lukenut oppimateriaalia. Jos jostain syystä omalla kurssillasi opetus ei riitä tehtävien tekemiseen, voit lukea lisäksi nettikurssin mooc.fi:stä.
Hei,
kyse tosiaan pakollisesta kurssista, vaikka itsestäni alan ammattilaista ole kuitenkaan tulossa. :)
Mun raapustus on tällainen, tuo c-kohta ei toimi.
import java.util.Scanner; public class Tehtavaoma { private static Scanner lukija = new Scanner(System.in); private static void teeA() { System.out.print("Mikä on nimesi? "); String nimi = lukija.nextLine(); System.out.println("Hei vain, " + nimi + "!"); char komento; do { System.out.print("Valitse: " + "B"); String rivi = lukija.nextLine(); if ( rivi.length() > 0 ) komento = rivi.charAt(0); else komento = 'ö'; switch (komento) { case 'B': teeB(); break; default: System.out.println("Virheellinen komento!"); break; } } while (komento!='L'); } private static void teeB() { System.out.print("Mikä on ikäsi? "); String ikä = lukija.nextLine(); System.out.println("Olet " + ikä + " vuotta vanha"); char komento; do { System.out.print("Valitse: " + "C "); String rivi = lukija.nextLine(); if ( rivi.length() > 0 ) komento = rivi.charAt(0); else komento = 'ö'; switch (komento) { case 'C': teeC(); break; default: System.out.println("Virheellinen komento!"); break; } } while (komento!='L'); } private static void teeC() { String nimi = lukija.nextLine(); String ikä = lukija.nextLine(); System.out.println("Nimesi on " + nimi + " ja olet " + ikä + " vuotta vanha."); char komento; do { System.out.print("Valitse: " + "C "); String rivi = lukija.nextLine(); if ( rivi.length() > 0 ) komento = rivi.charAt(0); else komento = 'ö'; switch (komento) { case 'L': teeL(); break; default: System.out.println("Virheellinen komento!"); break; } } while (komento!='L'); //miten tulostetaan nimi ja ikä? } private static void teeL() { System.out.println("Valitsit toiminnon L. Ohjelman suoritus päättyy."); } public static void main(String[] args) { char komento; do { System.out.print("Valitse: " + "A:"); String rivi = lukija.nextLine(); if ( rivi.length() > 0 ) komento = rivi.charAt(0); else komento = 'ö'; switch (komento) { case 'A': teeA(); break; default: System.out.println("Virheellinen komento!"); break; } } while (komento!='L'); } }
Mod. lisäsi kooditagit!
Nythän koodissasi vaadit, että ensin tulisi A, sitten B, sitten C ja sitten L, eikä tässä ole mitään järkeä. Tehtävässä varmaan tarkoitettiin, että samassa silmukassa (main-metodissa) hyväksyttäisiin mikä tahansa vaihtoehto. Siis tee vain yksi silmukka, jossa on tapaukset kaikille eri syötteille. Lisäksi selvästi olet toteuttanut kohdat A ja B väärin, koska tehtävässä ei käsketty tulostaa silloin mitään tervehdyksiä vaan vain kysyä tietoja. Tiedot pitäisi tallentaa muuttujiin, ja C-kohdassa sitten tulostettaisiin tieto näistä muuttujista ilman lisäkysymyksiä. (Nyt yrität C-kohdassa lukea uudestaan tietoja.)
Hyvä alku, mutta vähän menee ajatus sekaisin.
Laittaisin jotenkin alla olevan mukaisesti ensin alkuarvot muuttujille ja sitten muutetaan, jos tulee oikeanlainen syöte.
Ottaisin myös kaikki ääkköset pois koodista ja muuttujista, niiden kanssa on ollut ongelmia ohjelman kääntämisessä ja suorituksessa myös eivät tahdo näkyä oikein.
public static void main(String[] args) { Scanner lukija = new Scanner(System.in); char komento = 'z'; String nimi = "Nimi"; String ika = "0"; String syote = ""; System.out.println(""); System.out.println("Toiminnot:"); System.out.println(" - A (Nimi)"); System.out.println(" - B (Ika)"); System.out.println(" - C (Tulosta tiedot)"); System.out.println(" - L (Lopetus)"); do { System.out.println(""); System.out.println("Valitse: A, B, C tai L"); System.out.println(""); System.out.print(" -> valitse jotakin! -> "); String rivi = lukija.nextLine(); System.out.println(""); if ( rivi.length() > 0 ) { komento = rivi.charAt(0); } else { komento = 'z'; } switch (komento) { case 'A': System.out.print("Mika on nimesi? "); syote = lukija.nextLine(); if (tarkastanimi(syote)) { nimi = syote; } break; case 'B': System.out.print("Mika on ikasi? "); syote = lukija.nextLine(); if (tarkastaika(syote)) { ika = syote; } break; case 'C': System.out.println("Nimesi on " + nimi + " ja olet " + ika + " vuotta vanha."); System.out.println(""); break; case 'L': System.out.println("Lopetetaan ohjelma! "); System.out.println(""); break; default: System.out.println("Virheellinen komento!"); System.out.println(""); break; } } while (komento != 'L'); lukija.close(); }
Hei,
kiitos vastauksesta! :)
En silti saa tuota kohtaa c -tulosta nimi ja ikä toimimaan. Ehdottamallasi ohjelmalla antaa seuraavan tulosteen: Nimesi on Nimi ja olet 0 vuotta vanha. Onkohan tässä taas jokin pikku juttu mitä en vain käsitä...
Oletko syöttänyt noi A ja B kohdat ennen C:tä?
Syöte pitää vielä tarkastaa, ikä voisi mennä vaikka näin:
private static boolean tarkastaika(String sana1) { if (sana1.equals("")) sana1 = "error"; char[] chars1 = sana1.toCharArray(); for (char c : chars1) { if(!Character.isDigit(c) ) { System.out.println(""); System.out.println("Virheellinen syote: (" + sana1 + ")"); System.out.println(""); return false; } } int inputNumber = Integer.parseInt(sana1); if ((inputNumber > 0) && (inputNumber < 120)) { return true; } else { System.out.println(""); System.out.println("Numero ei kay!"); System.out.println(" 0 < IKA < 120 "); System.out.println(""); return false; } }
Sama asia lyhyemmin alla. Ja validoivissa funktioissa ei saa tulostaa. Javan hengessä voisi olla parempi vaikka päästää tuo NumberFormatException läpi ja heittää myös liian pienten ja suurten lukujen tapauksessa jonkinlainen poikkeus.
private static void validateAge(String input) { try { int num = Integer.parseInt(input.trim()); return num > 0 && num < 100; } catch (NumberFormatException e) { return false; } }
Kiitos Tapani!
Tuo ikä tosiaan menee noin. Osaisitko sanoa, mitä mulla mahtaa olla tässä väärin, kun nimeä yritän pähkäillä?
private static boolean tarkastanimi(String text) { String syote = text; if(syote.contains(" "))return false; if (!syote.trim().matches("[a-zåäöA-ZÅÄÖ-]+")){ } return true; } }
Mod. lisäsi kooditagit!
Sinulla on koodissasi ehtolause, jonka sisällä ei ole mitään. Siispä se ei myöskään vaikuta mihinkään. Tämän pitäisi oikeastaan olla ilmiselvää.
Joo, aika lähelle jo pääsitkin. Piti ihan googletella noita text.matches() -juttuja, kun niin harvoin niitä on tullut vastaan :-)
Muutama huomio:
1. text -parametriä ei oikeastaan tarvitse "syöttää" uuteen muuttujaan.
2. Jos annetussa nimessä on välilyönti -> se ei kelpaa.
3. Jos nimi sisältää vain aakkosia -> se ei kelpaa (jos return true siirretään sulkujen sisään).
4. Vaikka tarkastus tehdään "trimmaten", itse nimi säilyy ennallaan (trimmaamatta) pääohjelmassa.
Ehdottaisin taas jotakin alla olevan tapaista. Ehkä helpoin konsti voisi olla tarkastaa, että trimmatun nimen pituus > 0.
Oheinen hyväksyy Etunimi Sukunimi -yhdistelmän tai vain yhden nimen.
[Voisiko joku vielä avata, miksi ei saisi tulostella virheilmoituksia.]
private static boolean tarkastanimi(String text) { if (text.matches("[a-zåäöA-ZÅÄÖ-]+[ ]?[a-zåäöA-ZÅÄÖ-]*")){ return true; } else { System.out.println(""); System.out.println("Nimi ei kelpaa!"); System.out.println(""); return false; } }
TapaniS kirjoitti:
[Voisiko joku vielä avata, miksi ei saisi tulostella virheilmoituksia.]
Pointtina varmaankin, että on siistimpää käsitellä ja tulostella virheilmoitukset pääohjelman puolella, kun tuo funktio palauttaa tilan kuitenkin.
Kiitos jälleen :)
TapaniS kirjoitti:
Voisiko joku vielä avata, miksi ei saisi tulostella virheilmoituksia.
Nyt funktiosi sopii vain tilanteisiin, joissa halutaan tulostaa juuri nuo virheilmoitukset juuri tuolla tavalla. Jos vaikkapa luettaisiin tiedostosta sata nimeä ja tarkistettaisiin ne silmukassa, samaa funktiota ei voisi enää järkevästi käyttää, koska se tulostaisi paljon turhia tai epäselviä virheilmoituksia. Yleensä pyritään siihen, että samaa funktiota voi hyödyntää useassa tilanteessa.
Eikä aina edes haluta tulostaa yhtään mitään. Tai validatoreita voidaan ketjuttaa ja halutaan tulostaa vain yksi virheilmoitus. Tulostusta ei välttämättä tehdä konsoliin vaan näytölle tai tiedostoon jne.
Hei Tapani,
osaisitkohan auttaa minua tässäkin?
Tähän mennessä on:
import java.util.Scanner; public class kokonimi{ private static Scanner user_input; public static void main (String[]args) { user_input = new Scanner (System.in); String etunimi; System.out.print("Anna etunimesi: "); etunimi = user_input.next (); String sukunimi; System.out.print ("Anna sukunimesi: " ); sukunimi = user_input.next (); String kokonimi; kokonimi = sukunimi + ", " + etunimi; System.out.println ("kokonimesi on: " + kokonimi); } }
Tähän pitäisi lisäksi luoda taulukko, johon voi tallentaa 5 nimeä. Nimet kysytään käyttäjältä ja järjestetään sukunimen mukaiseen aakkosjärjestykseen.
T
Mod. poisti turhia lainauksia. Lainaa muiden viesteistä vain sellaisia kohtia, joita aiot erikseen kommentoida! Kokonaisen viestin kopiointi on hyödyntöntä ja sotkuista.
Moi,
Tottakai! Oikein perustehtävä tämmöinen. Tarvitset ainakin taulukkomuuttujat sekä laskurin, esim.
String[] etunimi = new String[5]; String[] sukunimi = new String[5]; String[] kokonimi = new String[5]; int laskuri = 0;
Sitten pitää kysyä ja lukea viisi kertaa etunimi ja sukunimi ja viedä tulos taulukkomuuttujaan, esim.
if (tarkastanimi(syote)) { etunimi[laskuri] = syote; }
laskurin arvo kasvaa aina yhdellä, jos saadaan kunnollinen etu- ja sukunimi. Muuten luetaan samalla laskurin arvolla etu- ja sukunimi uudestaan.
Lopuksi taulukko kokonimi lajitellaan ja tulostetaan.
import java.util.Arrays; Arrays.sort(kokonimi);
TapaniS kirjoitti:
Moi,
Tottakai! Oikein perustehtävä tämmöinen. Tarvitset ainakin taulukkomuuttujat sekä laskurin, esim.
Hei,
sain tehtyä, tosin uskoakseni hieman pidemmän kaavan kautta.
Kiitokset jälleen :)
Aihe on jo aika vanha, joten et voi enää vastata siihen.