IT rekvalifikácia. Seniorní programátori zarábajú až 6 000 €/mesiac a rekvalifikácia je prvým krokom. Zisti, ako na to!

14. diel - Textové reťazce v Jave do tretice - Split a join

V predchádzajúcom cvičení, Riešené úlohy k 13. lekcii Javy, sme si precvičili získané skúsenosti z predchádzajúcich lekcií.

V dnešnom Java tutoriále si vysvetlíme ďalšie metódy na reťazci, ktoré som vám zámerne zatajil, pretože sme nevedeli, že textový reťazec je vlastne pole :)

Metódy na reťazci

Keď si vytvoríme ľubovoľnú premennú a napíšeme za ňu potom bodku, zobrazí nám IDE ponuku všetkých metód a vlastností (a tiež premenných, ale k tomu sa dostaneme až pri objektoch), ktoré na ňu môžeme volať. Skúsme si to:

Metódy na textovom reťazci string v IntelliJ - Základné konštrukcie jazyka Java

Tú istú ponuku je možné vyvolať aj stlačením klávesov Ctrl + Medzerník v prípade, že kurzor umiestnime na bodku.

Samozrejme to platí pre všetky premenné a triedy a budeme to využívať čoraz častejšie. Metódy sú radené abecedne a môžeme nimi listovať pomocou kurzorových šípok. Popis metód (čo robia) a aké vyžadujú parametre môžeme v IntelliJ vyvolať tým, že nabehneme šípkami na metódu, o ktorej chceme vedieť viac, a stlačíme klávesy Ctrl + Q.

Povedzme si niečo o nasledujúcich metódach a ukážme si ich na jednoduchých príkladoch.

Metóda substring()

Vráti podreťazec od danej počiatočnej pozície do danej koncovej pozície:

System.out.println("Wolfgang Amadeus Mozart".substring(9, 16));

Výstup:

Konzolová aplikácia
Amadeus

Metóda compareTo()

Umožňuje porovnať dva reťazce podľa abecedy. Vracia hodnotu -1, ak je prvý reťazec pred reťazcom v parametri, hodnotu 0, ak sú rovnaké, a hodnotu 1, ak je za ním:

System.out.println("Argentina".compareTo("Barbados"));

Výstup:

Konzolová aplikácia
-1

Poďme sa teraz pozrieť na ďalšie metódy, ktoré sú naozaj veľmi užitočné.

Metódy split() a join()

Z predchádzajúceho tutoriálu vieme, že parsovanie reťazca po znaku môže byť niekedy celkom zložité a to sme robili pomerne jednoduchý príklad. S reťazcami sa samozrejme budeme stretávať stále, a to ako na vstupe od používateľa (napr. z konzoly alebo z polí v okenných aplikáciách), tak v súboroch TXT a XML. Veľmi často máme zadaný jeden dlhší textový reťazec (riadok súboru alebo riadok konzoly), v ktorom je viac hodnôt oddelených tzv. separátormi, napr. čiarkou. V tomto prípade hovoríme o formáte CSV (Comma-Separated Values, teda hodnoty oddelené čiarkou). Aby sme si boli istí, že vieme, o čom hovoríme, pozrime sa na nejaké ukážkové reťazce:

Jessie,Brown,Wall Street 10,New York 3,130 00
.. ... .-.. .- -. -.. ... --- ..-. -
(1,2,3;4,5,6;7,8,9)

Význam jednotlivých reťazcov:

  • Prvý reťazec je očividne nejaký používateľ, takto by sme mohli napr. realizovať uloženie používateľov do CSV súboru, každý na jeden riadok.
  • Druhý reťazec sú znaky Morseovej abecedy, separátorom (oddeľovačom) je tu medzera.
  • Tretí reťazec je matica s 3 stĺpcami a 3 riadkami. Oddeľovačom stĺpcov je čiarka, riadkov bodkočiarka.

Na type String môžeme volať metódu split(), ktorá berie ako parameter separátor. Následne pôvodný reťazec rozdelí podľa separátorov na pole podreťazcov, ktoré vráti. To nám veľmi uľahčí prácu pri rozdeľovaní hodnôt v reťazci.

Metóda join() sa volá priamo na type String a umožňuje nám naopak pole podreťazcov spojiť oddeľovačom do jediného reťazca, parametrami sú oddeľovač a pole. Výstupom metódy je výsledný reťazec.

Keďže nevieme tvoriť objekty (používateľov) a ani pracovať s viacrozmernými poľami (matice), skúsime si naprogramovať dekóder správ z Morseovej abecedy.

Dekóder Morseovej abecedy

Poďme si opäť pripraviť štruktúru programu. Budeme potrebovať 2 reťazce, jeden so správou v Morseovej abecede, druhý zatiaľ prázdny, doňho budeme ukladať výsledok nášho snaženia. Ďalej budeme ako v prípade samohlások potrebovať nejaký vzor písmen. K písmenám samozrejme vzor ich znaku v morzeovke. Písmená môžeme opäť uložiť do obyčajného reťazca, pretože majú iba jeden znak. Znaky Morseovej abecedy majú už znakov viac, tie musíme dať do poľa. Štruktúra nášho programu by teraz mohla vyzerať nasledovne:

// the string which we want to decode
String encryptedMessage = ".-.. . --- -. .- .-. -.. ---";
System.out.printf("The original message: %s%n", encryptedMessage);
// the string with a decoded message
String decodedMessage = "";

// array definitions
String alphabetChars = "abcdefghijklmnopqrstuvwxyz";
String[] morseChars = {".-", "-...", "-.-.", "-..", ".", "..-.", "--.", "....",
"..", ".---", "-.-", ".-..", "--", "-.", "---", ".--.", "--.-", ".-.", "...", "-", "..-",
"...-", ".--", "-..-", "-.--", "--.."};

Môžete si potom pridať ďalšie znaky ako čísla a interpunkčné znamienka, my ich tu vynecháme.

Teraz si reťazec encryptedMessage rozbijeme metódou split() na pole podreťazcov obsahujúcich jednotlivé znaky morzeovky. Rozdeľovať budeme podľa znaku medzery. Pole následne preiterujeme cyklom foreach:

// splitting the string into Morse characters
String[] characters = encryptedMessage.split(" ");

// iterating over Morse characters
for (String morseChar : characters) {

}

Ideálne by sme sa mali nejako vysporiadať s prípadmi, kde používateľ zadá napr. viac medzier medzi znakmi (to používatelia radi robia). Metóda split() potom vytvorí o jeden reťazec v poli viac, ktorý bude prázdny. Ten by sme mali potom v cykle detekovať a ignorovať, my sa s tým v tutoriáli nebudeme zaoberať.

V cykle sa pokúsime nájsť aktuálne čítaný znak morzeovky v poli morseChars. Bude nás zaujímať jeho index, pretože keď sa pozrieme na ten istý index v poli alphabetChars, bude tam zodpovedajúce písmeno. To je samozrejme z toho dôvodu, že pole aj reťazec obsahujú rovnaké znaky zoradené podľa abecedy. Umiestnime do tela cyklu nasledujúci kód:

char alphabetChar = '?';

int index = -1;
for (int i = 0; i < morseChars.length; i++) {
    if (morseChars[i].equals(morseChar))
        index = i;
}

if (index >= 0) { // character was found
    alphabetChar = alphabetChars.charAt(index);
}
decodedMessage += alphabetChar;

Kód najskôr do abecedného znaku (alphabetChar) uloží znak ?, pretože sa môže stať, že znak v našej sade nemáme. Následne sa pokúsime zistiť jeho index. Pole v Jave bohužiaľ nemá metódu indexOf() a zatiaľ nechcem zabiehať do zložitejších dátových štruktúr. Napíšeme si teda vyhľadanie typu String v poli sami, bude to celkom jednoduché.

Vyhľadanie reťazca v poli

Najprv nastavíme index na -1, pretože nevieme, či pole daný String (Morseov znak) obsahuje. Následne pole prejdeme cyklom a budeme kontrolovať jednotlivé reťazce s naším stringom (znakom). Už vieme, že na porovnanie dvoch reťazcov musíme použiť metódu equals(). Ak reťazce súhlasia, uložíme si aktuálny index.

Ak sme znak našli (index >= 0), dosadíme do premennej alphabetChar znak z abecedy pod týmto indexom. Nakoniec znak pripojíme ku správe. Operátor += nahrádza decodedMessage = decodedMessage + alphabetChar.

Na záver samozrejme správu vypíšeme:

System.out.printf("Decoded message: %s%n", decodedMessage);

Výstup programu:

Konzolová aplikácia
Original  message: .-.. . --- -. .- .-. -.. ---
Decoded message: leonardo

Hotovo! Za úlohu máte naprogramovať si program opačný, ktorý naopak zakóduje reťazec do morzeovky, kód bude veľmi podobný. S metódami split() a join() sa stretneme počas Java kurzu ešte niekoľkokrát.

Špeciálne znaky a escapovanie

Textový reťazec môže obsahovať špeciálne znaky, ktoré sú predsadené spätnou lomkou \. Je to najmä sekvencia \n, ktorá kdekoľvek v texte spôsobí odriadkovanie a potom \t, kde sa jedná o tabulátor. Sekvenciu \n do kódu často nepíšeme a využijeme radšej formátový špecifikátor %n, ktorý spôsobí správne odriadkovanie na špecifických platformách. Poďme si to vyskúšať:

System.out.println("First line\nSecond line");

Znak \ označuje nejakú špeciálnu sekvenciu znakov v reťazci a je ďalej využívaný napr. na písanie Unicode znaku ako "\uxxxx", kde xxxx je kód znaku.

Problém môže nastať vo chvíli, keď chceme napísať samotné lomítko \, musíme ho tzv. odescapovať:

System.out.println("This is a backslash: \\");

Rovnakým spôsobom môžeme odescapovať napr. úvodzovku tak, aby ju Java nechápala ako koniec reťazca:

System.out.println("This is a quotation mark: \"");

Vstupy z konzoly a polí v okenných aplikáciách sa samozrejme escapujú samy, aby používateľ nemohol zadať sekvenciu \n a podobne. V kóde to má programátor povolené a musí na to myslieť.

Týmto sme v podstate zakončili kurz o základnej štruktúre jazyka Java. V nasledujúcich lekciách si uvedieme viacrozmerné polia a matematické operácie. Zo základných konštrukcií jazyka vás tu ale už nič neprekvapí :-) V podstate by ste už pokojne mohli ísť aj na objekty, odporúčam ale zvyšné tutoriály ešte aspoň prejsť, jedná sa predsa len o základné znalosti, ktoré by ste mali mať.

V nasledujúcom kvíze, Kvíz - Textové reťazce v Jave, si vyskúšame nadobudnuté skúsenosti z predchádzajúcich lekcií.


 

Mal si s čímkoľvek problém? Stiahni si vzorovú aplikáciu nižšie a porovnaj ju so svojím projektom, chybu tak ľahko nájdeš.

Stiahnuť

Stiahnutím nasledujúceho súboru súhlasíš s licenčnými podmienkami

Stiahnuté 13x (2.52 kB)
Aplikácia je vrátane zdrojových kódov v jazyku Java

 

Predchádzajúci článok
Riešené úlohy k 13. lekcii Javy
Všetky články v sekcii
Základné konštrukcie jazyka Java
Preskočiť článok
(neodporúčame)
Kvíz - Textové reťazce v Jave
Článok pre vás napísal David Hartinger
Avatar
Užívateľské hodnotenie:
33 hlasov
David je zakladatelem ITnetwork a programování se profesionálně věnuje 15 let. Má rád Nirvanu, nemovitosti a svobodu podnikání.
Unicorn university David sa informačné technológie naučil na Unicorn University - prestížnej súkromnej vysokej škole IT a ekonómie.
Aktivity