Lekce 9 - Pole v JavaScriptu
V předešlém cvičení, Řešené úlohy k 7.-8. lekci JavaScriptu, jsme si procvičili nabyté zkušenosti z předchozích lekcí.
V dnešním tutoriálu základů JavaScriptu si představíme datovou strukturu pole a vyzkoušíme si, co všechno umí.
Pole v JavaScriptu
Představme si, že si chceme uložit nějaké údaje o více
prvcích. Například chceme v paměti uchovávat deset čísel,
políčka šachovnice nebo jména registrovaných uživatelů. Asi nám dojde,
že v programování bude nějaká lepší cesta, než začít vytvářet
proměnné uzivatel1
, uzivatel2
až
uzivatel50
. Nehledě na to, že jich může být třeba 1000!
Tento problém nám řeší pole, ve kterém lze
uchovávat větší množství proměnných. Můžeme si ho
představit jako řadu přihrádek, v každé pak máme uložený jeden prvek.
Přihrádky jsou očíslované tzv. indexy,
první má index 0
:
(Na obrázku je vidět pole osmi čísel.)
Velikost pole je možné měnit za běhu programu a do stejného pole lze ukládat různé datové typy. V některých jazycích musíme při vytváření pole zadat jeho přesnou velikost a datový typ proměnných, které chceme ukládat. Datový typ pak musí být stejný pro všechny prvky v poli. V JavaScriptu nemusíme specifikovat vůbec nic.
Výhody pole
Pole je jednoduchou datovou strukturou. Jeho prvky jsou v paměti jednoduše uloženy za sebou, proto se k nim pomocí indexů rychle přistupuje. Mnoho vestavěných funkcí a metod v JavaScriptu pracuje s poli nebo pole vrací. Je to klíčová struktura.
Pole úzce souvisí s cykly, protože se potom používají na manipulaci s prvky.
Práce s polem
Nyní si již ukážeme, jak s polem pracovat. V JavaScriptu můžeme deklarovat pole a zároveň ho inicializovat daty nebo ho můžeme deklarovat jako prázdné a později ho daty naplnit.
Vytvoření pole
Pole vytvoříme pomocí objektu Array
a klíčového slova
new
, ke kterému se podrobně dostaneme až v kurzu OOP. Uvedeme jen, že pole je referenční
(můžeme chápat jako složitější) datový typ:
let cisla = new Array();
Následující kód funguje úplně stejně jako ten výše, ale je kratší. Proto tento zápis polí budeme preferovat:
let cisla = [];
Hranaté závorky []
na české klávesnici
zapíšeme pomocí pravého ALT a znaků F a
G:
Přístup k prvkům pole
K prvkům pole potom přistupujeme také přes hranatou závorku. Pojďme na
první index (tedy index 0
) uložit číslo 1
:
let cisla = []; cisla[0] = 1;
Nyní vytvoříme pole představující nákupní košík a vložíme do něj nějaké ovoce. Následně vložené položky vypíšeme:
let kosik = []; // máme prázdný košík kosik[0] = "jablko"; // jako první do košíku vložíme jablko kosik[1] = "banán"; // na druhé místo přidáme banán document.write(kosik[0] + "<br>" + kosik[1]); // obsah košíku poté vypíšeme
Pro deklaraci pole bychom stejně dobře mohli použít
konstantu jako const kosik = []
. Pole v konstantě bychom
následně mohli libovolně upravovat. Pouze by do dané konstanty
nešla vložit jiná hodnota, např. jiné pole.
Naplnění pole cyklem
Chceme-li naplnit pole čísly od 1
do 10
, nebudeme
to dělat ručně, ale využijeme cyklus for
:
let cisla = []; for (let i = 0; i < 10; i++) { cisla[i] = i + 1; }
Abychom pole vypsali, stačí za předchozí kód připsat:
for (let i = 0; i < cisla.length; i++) { document.write(cisla[i] + " "); }
Ve výpisu jsme použili vlastnost length
, ve
které je uložena délka pole, tedy počet jeho prvků.
Cyklus for...of
Pro čtení prvků pole můžeme použít zjednodušenou verzi cyklu pro práci s kolekcemi, známou někdy jako cyklus foreach. Ten projede všechny prvky v poli, délku pole pak tedy nemusíme zjišťovat. Jeho syntaxe je následující:
for (let nazevPromenne of nazevPole) { // příkazy }
Cyklus projede prvky v kolekci (to je obecný název pro struktury, které obsahují více prvků, u nás to bude pole) postupně od prvního do posledního.
V minulosti se pro procházení polí v JavaScriptu
používal i cyklus for...in
. Ten ovšem do proměnné neukládá
prvek, ale index, což je pro tento účel matoucí.
Přepišme tedy náš dosavadní program a pro výpis použijme cyklus
for...of
. Tento cyklus nemá řídící proměnnou
a není tedy vhodný pro vytvoření našeho pole. Použijeme ho proto jen pro
výpis:
let cisla = []; for (let i = 0; i < 10; i++) { cisla[i] = i + 1; } for (let cislo of cisla) { document.write(cislo + " "); }
Aktuálně získaný prvek máme v každé iteraci cyklu
uložený v proměnné cislo
.
Výsledek v prohlížeči:
Položky v poli můžeme také převést na textový řetězec
pomocí metody join()
, kterou jsme zmiňovali v lekci Textové
řetězce v JavaScriptu. Místo cyklu pro výpis bychom tedy napsali
document.write(cisla.join(' '));
. Pokud žádný oddělovač
nespecifikujeme, použije se jako výchozí oddělovač čárka bez mezery.
Naplnění pole výčtem prvků
Pole samozřejmě můžeme naplnit ručně i bez toho, abychom dosazovali jeho položky postupně do každého indexu. Jednoduše je v hranatých závorkách uvedeme všechny a oddělíme je čárkou. Textové řetězce zapisujeme samozřejmě s uvozovkami:
let dny = ["neděle", "pondělí", "úterý", "středa", "čtvrtek", "pátek", "sobota"];
Rozšiřme si ještě tento příklad. Zjistíme aktuální datum a pomocí
metody getDay()
získáme číslo od 0
do
6
, které odpovídá danému dni v týdnu. Vrácená hodnota
vychází z americkém vnímání týdne a začíná nedělí. Neděli tedy
vložíme do pole jako první (na index 0
) a posledním dnem v poli
bude sobota:
let dny = ["neděle", "pondělí", "úterý", "středa", "čtvrtek", "pátek", "sobota"]; let dnes = new Date(); let denTydne = dnes.getDay(); document.write("Dnes je " + dny[denTydne]);
Skript vytvoří pole textových řetězců s názvy dnů. Pak zjistí
aktuální datum a uloží je do proměnné dnes
. Metoda
getDay()
vrátí číslo dne v týdnu pro aktuální datum. To
uložíme do proměnné denTydne
, kterou předáme jako index
našemu poli a získáme tak odpovídající název dne z pole:
Když říkáme, že nám metoda něco vrátí, máme tím na mysli, že metoda nám poskytne nějakou hodnotu jako výsledek své činnosti. Získanou hodnotu pak můžeme uložit do proměnné, vypsat na obrazovku, použít v dalším výpočtu a podobně.
Práce s prvky v poli
Pojďme si nyní popsat některé metody, které při práci s poli využijeme.
Pro přidání nového prvku do pole máme k dispozici dvě
metody. Metoda push()
vloží novou položku na konec
pole. Metoda unshift()
ji vloží na začátek
pole:
let dny = ["pondělí", "úterý", "středa", "čtvrtek", "pátek"]; dny.push("sobota"); // sobotu vloží na konec pole dny.unshift("neděle"); // neděli vloží na začátek pole
Všimněte si, že na rozdíl od metod na řetězcích, které vracely upravený řetězec, metody na poli dané pole rovnou mění.
Pro odebrání prvku z pole využijeme metody
pop()
a shift()
. První odebere položku, která je
na konci pole, druhá smaže první prvek v
poli:
let dny = ["neděle", "pondělí", "úterý", "středa", "čtvrtek", "pátek", "sobota"]; dny.pop(); // odstraní se sobota dny.shift(); // odstraní se neděle
Metoda splice()
Pokud chceme vložit nebo odstranit prvek, který není ani na začátku ani
na konci pole, použijeme na modifikaci pole metodu splice()
.
Jako první parametr bere index prvku, od kterého bude pole upraveno. Druhý parametr je volitelný a specifikujeme v něm, kolik prvků má být modifikováno. Pokud jej neuvedeme, provede se úprava až do konce pole. Následují další volitelné parametry, v nichž uvádíme položky, které chceme do pole přidat nebo jimi nahradit stávající prvky.
Ukažme si nejprve mazání prvků:
let ovoce = ["jablko", "hruška", "banán", "malina", "jahoda", "meruňka", "kiwi", "švestka"]; ovoce.splice(2, 3); // výstup: ["jablko", "hruška", "meruňka", "kiwi", "švestka"] ovoce.splice(3); // výstup: ["jablko", "hruška", "meruňka"]
Nejprve jsme smazali tři prvky počínaje indexem 2
. Z pole
nám tedy zmizel banán, malina a jahoda. Potom jsme znovu zavolali metodu
splice()
s jedním parametrem, čímž jsme smazali prvky s indexem
3
a výš.
Metoda splice()
umí také přidávat nové
prvky. První parametr určí pozici vkládaného prvku, do druhého zadáme
0
a jako třetí doplníme prvek, který chceme vložit. Do ukázky
výše tedy doplníme další řádek:
ovoce.splice(2, 0, "malina"); // výstup: ["jablko", "hruška", "malina", "meruňka"]
Pokud chceme prvek nahradit, zadáme do druhého parametru
1
:
ovoce.splice(0, 1, "banán"); // výstup: ["banán", "hruška", "malina", "meruňka"]
Nakonec budeme chtít nahradit banán i hrušku. Do ukázky přidáme poslední řádek:
ovoce.splice(0, 2, "jahoda", "jablko"); // výstup: ["jahoda", "jablko", "malina", "meruňka"]
Řazení prvků v poli
Položky v poli lze jednoduše seřadit
metodou sort()
. Tato metoda nám seřadí textové
řetězce podle abecedy (vzestupně):
let jmena = ["Dan", "Bohouš", "Cyril", "Anna"]; jmena.sort(); // výstup: ["Anna", "Bohouš", "Cyril", "Dan"]
Pořadí prvků v poli můžeme otočit
pomocí metody reverse()
:
jmena.reverse(); // výstup: ["Dan", "Cyril", "Bohouš", "Anna"]
Pokud máme v poli čísla, metoda sort()
je
seřadí jako textové řetězce:
let cisla = [5, 3, 30, 25]; cisla.sort(); // výstup: [25, 3, 30, 5]
Tento výpis je ale správně pouze lexikograficky, nikoliv tak, jak jsme měli v úmyslu. Abychom docílili správného výsledku, musíme metodě přidat anonymní funkci, v níž určíme, podle čeho má prvky našeho pole porovnat. Použijeme tedy následující zápis:
let cisla = [5, 3, 30, 25]; cisla.sort(function(a, b) { return a - b }); // výstup: [3, 5, 25, 30]
Funkcím se budeme věnovat v lekci Funkce v JavaScriptu.
Jednoduše řečeno zde metodě sort()
určíme, že má zjistit
rozdíl mezi dvěma prvky (a - b
). Pokud je a
větší
než b
, získáme kladnou hodnotu a metoda tato čísla prohodí. V
opačném případě zůstane pořadí zachováno. Porovnávání položek v
poli probíhá opakovaně až do chvíle, kdy jsou všechny prvky pole na
správných pozicích a pole je celé seřazeno.
Práce s dvourozměrným polem
Na závěr si dnes představíme pole, které obsahuje další pole jako své prvky.
V následujícím příkladu vytvoříme skript vypisující, kdo má dnes svátek. Nejprve si vytvoříme pole, kam budeme ukládat další pole, ve kterém budou uloženy svátky v daném měsíci. Využijeme tedy právě dvourozměrné pole, přesněji pole polí. Postupně takto doplníme položky se všemi jmény v roce.
Poté zjistíme aktuální datum a pomocí metody getDate()
získáme číslo dne. Metoda vrací hodnotu 1
až
31
, pokud tedy chceme získat odpovídající index v
poli pro aktuální den, musíme odečíst 1
. Pořadové
číslo měsíce získáme metodou getMonth()
. Ta vrací hodnotu od
0
do 11
, kde 0
odpovídá lednu a
11
prosinci, získanou hodnotu tedy již nemusíme upravovat.
Nakonec vybereme hledaný prvek v poli polí, použijeme tedy nejprve index
měsíce a poté index dne:
// Tento skript pochází z webu itnetwork.cz // Smí být libovolně používán i modifikován, ale nesmí z něj být umazán tento text // vytvoříme si prázdné pole měsíců a postupně do něj přidáme pole se svátky v daném měsíci let mesice = []; // leden mesice.push(["Nový rok, Den obnovy samostatného českého státu", "Karina", "Radmila", "Diana", "Dalimil", "Tři králové", "Vilma", "Čestmír", "Vladan", "Břetislav", "Bohdana", "Pravoslav", "Edita", "Radovan", "Alice", "Ctirad", "Drahoslav", "Vladislav", "Doubravka", "Ilona", "Běla", "Slavomír", "Zdeněk", "Milena", "Miloš", "Zora", "Ingrid", "Otýlie", "Zdislava", "Robin", "Marika"]); // únor mesice.push(["Hynek", "Nela", "Blažej", "Jarmila", "Dobromila", "Vanda", "Veronika", "Milada", "Apolena", "Mojmír", "Božena", "Slavěna", "Věnceslav", "Valentýn", "Jiřina", "Ljuba", "Miloslava", "Gizela", "Patrik", "Oldřich", "Lenka", "Petr", "Svatopluk", "Matěj", "Liliana", "Dorota", "Alexandr", "Lumír", "Horymír"]); // březen mesice.push(["Bedřich", "Anežka", "Kamil", "Stela", "Kazimír", "Miroslav", "Tomáš", "Gabriela", "Františka", "Viktorie", "Anděla", "Řehoř", "Růžena", "Rút, Matylda", "Ida", "Elena, Herbert", "Vlastimil", "Eduard", "Josef", "Světlana", "Radek", "Leona", "Ivona", "Gabriel", "Marián", "Emanuel", "Dita", "Soňa", "Taťána", "Arnošt", "Kvido"]); // duben mesice.push(["Hugo", "Erika", "Richard", "Ivana", "Miroslava", "Vendula", "Heřman, Hermína", "Ema", "Dušan", "Darja", "Izabela", "Julius", "Aleš", "Vincenc", "Anastázie", "Irena", "Rudolf", "Valérie", "Rostislav", "Marcela", "Alexandra", "Evženie", "Vojtěch", "Jiří", "Marek", "Oto", "Jaroslav", "Vlastislav", "Robert", "Blahoslav"]); // květen mesice.push(["Svátek práce", "Zikmund", "Alexej", "Květoslav", "Klaudie", "Radoslav", "Stanislav", "Den vítězství", "Ctibor", "Blažena", "Svatava", "Pankrác", "Servác", "Bonifác", "Žofie", "Přemysl", "Aneta", "Nataša", "Ivo", "Zbyšek", "Monika", "Emil", "Vladimír", "Jana", "Viola", "Filip", "Valdemar", "Vilém", "Maxmilián", "Ferdinand", "Kamila"]); // červen mesice.push(["Laura", "Jarmil", "Tamara", "Dalibor", "Dobroslav", "Norbert", "Iveta, Slavoj", "Medard", "Stanislava", "Gita", "Bruno", "Antonie", "Antonín", "Roland", "Vít", "Zbyněk", "Adolf", "Milan", "Leoš", "Květa", "Alois", "Pavla", "Zdeňka", "Jan", "Ivan", "Adriana", "Ladislav", "Lubomír", "Petr a Pavel", "Šárka"]); // červenec mesice.push(["Jaroslava", "Patricie", "Radomír", "Prokop", "Cyril, Metoděj", "Den upálení mistra Jana Husa", "Bohuslava", "Nora", "Drahoslava", "Libuše, Amálie", "Olga", "Bořek", "Markéta", "Karolína", "Jindřich", "Luboš", "Martina", "Drahomíra", "Čeněk", "Ilja", "Vítězslav", "Magdaléna", "Libor", "Kristýna", "Jakub", "Anna", "Věroslav", "Viktor", "Marta", "Bořivoj", "Ignác"]); // srpen mesice.push(["Oskar", "Gustav", "Miluše", "Dominik", "Kristián", "Oldřiška", "Lada", "Soběslav", "Roman", "Vavřinec", "Zuzana", "Klára", "Alena", "Alan", "Hana", "Jáchym", "Petra", "Helena", "Ludvík", "Bernard", "Johana", "Bohuslav", "Sandra", "Bartoloměj", "Radim", "Luděk", "Otakar", "Augustýn", "Evelína", "Vladěna", "Pavlína"]); // září mesice.push(["Linda, Samuel", "Adéla", "Bronislav", "Jindřiška", "Boris", "Boleslav", "Regína", "Mariana", "Daniela", "Irma", "Denisa", "Marie", "Lubor", "Radka", "Jolana", "Ludmila", "Naděžda", "Kryštof", "Zita", "Oleg", "Matouš", "Darina", "Berta", "Jaromír", "Zlata", "Andrea", "Jonáš", "Václav, Den české státnosti", "Michal", "Jeroným"]); // říjen mesice.push(["Igor", "Olivie, Oliver", "Bohumil", "František", "Eliška", "Hanuš", "Justýna", "Věra", "Štefan, Sára", "Marina", "Andrej", "Marcel", "Renáta", "Agáta", "Tereza", "Havel", "Hedvika", "Lukáš", "Michaela", "Vendelín", "Brigita", "Sabina", "Teodor", "Nina", "Beáta", "Erik", "Šarlota, Zoe", "Den vzniku samostatného československého státu", "Silvie", "Tadeáš", "Štěpánka"]); // listopad mesice.push(["Felix", "Památka zesnulých (dušičky)", "Hubert", "Karel", "Miriam", "Liběna", "Saskie", "Bohumír", "Bohdan", "Evžen", "Martin", "Benedikt", "Tibor", "Sáva", "Leopold", "Otmar", "Mahulena, Den boje za svobodu a demokracii", "Romana", "Alžběta", "Nikola", "Albert", "Cecílie", "Klement", "Emílie", "Kateřina", "Artur", "Xenie", "René", "Zina", "Ondřej"]); // prosinec mesice.push(["Iva", "Blanka", "Svatoslav", "Barbora", "Jitka", "Mikuláš", "Benjamín", "Květoslava", "Vratislav", "Julie", "Dana", "Simona", "Lucie", "Lýdie", "Radana", "Albína", "Daniel", "Miloslav", "Ester", "Dagmar", "Natálie", "Šimon", "Vlasta", "Adam, Eva, Štědrý den", "1. svátek vánoční", "Štěpán, 2. svátek vánoční", "Žaneta", "Bohumila", "Judita", "David", "Silvestr"]); // nyní přistoupíme k samotnému výpisu let dnes = new Date(); let den = dnes.getDate()-1; let mesic = dnes.getMonth(); document.write("Dnes má svátek " + mesice[mesic][den]);
Výsledek:
V následujícím cvičení, Řešené úlohy k 9. lekci JavaScriptu, si procvičíme nabyté zkušenosti z předchozích lekcí.
Měl jsi s čímkoli problém? Stáhni si vzorovou aplikaci níže a porovnej ji se svým projektem, chybu tak snadno najdeš.
Stáhnout
Stažením následujícího souboru souhlasíš s licenčními podmínkami
Staženo 799x (6.63 kB)
Aplikace je včetně zdrojových kódů v jazyce JavaScript