Referenční typy - pole

Website: Moodle ZČU
Kurs: KPV/TI Technická informatika ve strojírenství - šablona
Buch: Referenční typy - pole
Gedruckt von: Nepřihlášený host
Datum: Montag, 9. November 2026, 10:54

1. Referenční typy

Referenční datové typy jsou ukládány na haldě (anglicky „Heap“) v podobě odkazu (reference) na objekty (složitější typy) oproti přímému uložení paměti (v zásobníku - anglicky "Stack"), jako je tomu u hodnotových typů. Pokud tedy nějaký podprogram – v C# obecně nazvaný jako metoda – skončí, je přidělená paměť zásobníku automaticky uvolněna. Paměť zásobníku je uspořádána ve formě na sobě položených schránek.

U haldy je paměť uvolněna až tehdy, když zanikne poslední odkaz na objekt. Paměť haldy je ve formě volně pohozených schránek, kde každá schránka má jmenovku (informaci, zda je používána). Když je vytvářen nový objekt, je vyhledána prázdná schránka a je přidělena objektu – odkaz na objekt je uložen do lokální proměnné uložené v zásobníku.

2. Pole

Dosud jsme pracovali s různými datovými typy. Co když ale potřebujeme pracovat s větším počtem hodnot, které jsou stejného datového typu. Asi uznáte, že nemá cenu deklarovat např. tisíc proměnných stejného datového typu, abychom v nich ukládali hodnoty. Pro tyto účely jsou vhodná pole, zejména pokud potřebujeme provádět stejné operace na všech hodnotách.

Typ pole (anglicky „Array“) tvoří skupina prvků stejného datového typu (jedná se tedy homogenní datovou strukturu např. na rozdíl od struktury). Tyto prvky pole jsou očíslovány, tzv. indexovány. S těmito prvky tedy pracujeme pomocí jejich pořadových čísel – indexů. Počáteční prvek má vždy index 0, takže pokud pole obsahuje N prvků, index posledního prvek je N-1. Počet prvků pole zjistíme pomocí vlastnosti Length. Na rozdíl od metody u vlastnosti nemusíme používat kulaté závorky uváděné na konci.

S poli pracujeme pomocí referencí – je to referenční typ. To tedy znamená, že proměnná typu pole odkazuje na blok paměti s prvky pole umístěných na haldě (anglicky „Heap“). Všechna pole jsou instancemi třídy System.Array prostředí .NET Framework.

Deklaraci pole lze zjednodušeně zapsat jako:

  • Jednorozměrné pole:

datovýTyp [] seznamIdentifikátorů;

  • Dvourozměrné pole:
datovýTyp [ , ] seznamIdentifikátorů;

apod.,

kde:

  • datovýTyp - je datový typ všech prvků tohoto pole (pro všechny je stejný). U datového typu nejsme omezeni pouze na primitivní datové typy. Můžeme vytvářet pole struktur, výčtových typů a tříd. Následující prázdné hranaté závorky identifikují, že se jedná o typ pole (ne o pouhou proměnnou)
  • seznamIdentifikátorů - vyjadřuje seznam deklarovaných identifikátorů deklarovaných odkazů (jednoduše řečeno proměnná typu pole obsahuje odkaz na pole s jednotlivými prvky, ve kterých jsou uloženy hodnoty – s poli tedy pracujeme pomocí referencí). V deklaraci neuvádíme počet prvků pole, ten určíme později, až budeme pole vytvářet. [3], [6]


3. Jednorozměrné pole

Prvním typem deklarace pole s prázdnými hranatými závorkami definujeme jednorozměrné pole, označované také jako vektor (přestavme si jej jako prvky uspořádané za sebou). 


Ilustrativní příklad PoleLidiDeklarace
Program PoleLidiDeklarace
  • Popis: Deklarace jednorozměrného pole, velikost pole, instance pole
  • Zadání: Deklarujte jednorozměrné pole s názvem poctyLidi, které bude obsahovat počty lidí v jednotlivých úsecích podniku. V podniku je 5 úseků.  
  • Řešení: Bude postupně probráno v následujícím textu


Následující kód představuje příklad deklarace jednorozměrného pole s celočíselnými prvky. Do těchto prvků budeme ukládat počet lidí v jednotlivých úsecích podniku, proto jej nazveme poctyLidi. Názvy polí je vhodné je pojmenovat množným číslem.

//Deklarace jednorozměrného pole
int[] poctyLidi;

Kód 1: Příklad deklarace jednorozměrného pole

K vytvoření instance pole se užívá klíčové slovo new. Tento operátor vrátí odkaz na nově vytvořené pole. Za operátorem new se uvádí datový typ prvků. Za datovým typem se uvádí v hranatých závorkách počet prvků pole – viz Kód 2. Zkusme si vytvořit pole o 5 celočíselných prvcích, kde každý prvek bude obsahovat počet lidí v jednotlivých úsecích podniku.

//Vytvoření instance pole o 5 prvcích
poctyLidi = new int[5];

Kód 2: Deklarace jednorozměrného pole poctyLidi o 5 celočíselných prvcích


Následující obrázek reprezentuje rozdíl mezi uložením v paměti u proměnné datového typu int a datového typu pole o pěti prvcích - viz Obrázek 1. Proměnná x datového typu int je alokována standardně v zásobníku, zatímco proměnná poctyLidi datového typu pole (v našem případě jednorozměrné pole) odkazuje na souvislý blok paměti, ve které jsou na haldě uloženy prvky pole. Pole je referenčního typu (bez ohledu na datový typ jeho prvků). Hodnoty prvků pole jsou automaticky inicializovány v závislosti na jejich datovém typu (u datového typu int je to 0).

Deklarace a inicializace proměnné datového typu int a deklarace a vytvoření instance pole

Obrázek 1: Deklarace a inicializace proměnné datového typu int a deklarace a vytvoření instance pole

Paměť pro instanci pole je přidělována dynamicky, velikost pole nemusí být konstanta, ale lze ji měnit za běhu programu (anglicky „Runtime“) – viz Kód 3.

//Výpis pro uživatele
Console.Write("Zadejte velikost pole: ");
//Načtení velikosti pole
int velikostPole = int.Parse(Console.ReadLine());
//Vytvoření instance pole o načtené velikosti
int[] poctyLidi = new int[velikostPole];

Kód 3: Příklad deklarace jednorozměrného pole, vytvoření instance, určení velikosti pole za běhu programu

Lze také vytvořit pole o velikosti 0 (pole o velikosti nula je stále pole o žádném prvku, takže se nejedná o nulovatelný datový typ – null).



4. Inicializace pole

Již jsme zmínili, že hodnoty prvků pole jsou automaticky inicializovány v závislosti na jejich datovém typu. Této inicializaci můžeme předejít specifikováním konkrétních hodnot u prvků pole oddělených čárkami ve složených závorkách.


Ilustrativní příklad PoleLidiInicializace
Program PoleLidiInicializace
  • Popis: Inicializace celočíselného pole
  • Zadání: Vytvořte instanci jednorozměrného celočíselného pole o 5 prvcích: 7, 5, 2, 4, 9. Instance se bude jmenovat poctyLidi
  • Řešení: Bude postupně probráno v následujícím textu


Zkusme inicializovat vlastními hodnotami jednorozměrné pole pocetLidi – viz Kód 1. Počet hodnot ve složených závorkách musí odpovídat definované velikosti pole. Hodnoty ve složených závorkách nemusí být konstanty, ale mohou to být i hodnoty vygenerované za běhu programu (např. náhodná čísla).

//Vytvoření instance pole o 5 prvcích včetně inicializace
int[] poctyLidi = new int[5] { 7, 5, 2, 4, 9 };

Kód 1: Příklad deklarace jednorozměrného pole s určením velikosti pole, vytvoření instance včetně inicializace

Určení velikosti pole lze také vynechat. Kompilátor si odvodí velikost pole z počtu hodnot uvedených ve složených závorkách – viz Kód 2.

/*Vytvoření instance pole o 5 prvcích včetně inicializace, kde
 * velikost pole je odvozena kompilátorem*/
int[] poctyLidi = { 7, 5, 2, 4, 9 };

Kód 2: Příklad deklarace jednorozměrného pole s odvozením velikosti pole, vytvoření instance včetně inicializace

Následující obrázek odráží podstatu předchozího kódu, který alokuje místo v paměti pro uložení pole - viz Obrázek 1.

Deklarace jednorozměrného pole poctyLidi včetně inicializace

Obrázek 1: Deklarace jednorozměrného pole poctyLidi včetně inicializace

Pole také může obsahovat struktury, nebo instance třídy. Inicializace probíhá tak, že každý jeho prvek vytvoříme zavoláním konstruktoru struktury, nebo třídy.


Ilustrativní příklad PoleStrukturInicializace
Program PoleStrukturInicializace
  • Popis: Deklarace jednorozměrného pole obsahující jednotlivé struktury
  • Zadání: Zkuste deklarovat pole struktur, které bude obsahovat prvky, které obsahují strukturu Cas. Jednotlivé struktury jsou inicializovány vlastním konstruktorem. Struktura bude obsahovat tři celočíselné datové složky (datový typ int):
    • hodiny – počet hodin
    • minuty – počet minut
    • sekundy – počet sekund

      Konstruktor struktury bude přijímat tři formální parametry: hodiny, minuty, sekundy. Pomocí hodnot těchto parametrů nastavte datové složky struktury Cas. Vytvořte v metodě Main pole struktur poleStruktur obsahující dva prvky struktury Cas vytvořených pomocí zavolání konstruktoru struktury. Inicializujte první prvek (struktury) pole hodnotami: 12, 30, 50 a druhý prvek: 5, 30, 6
  • Řešení: Řešení bude postupně probráno v následujícím textu

Následující příklad popisuje vytvoření pole struktur pomocí volání konstruktoru u jednotlivých prvků, tzn. jednotlivých struktur. Deklarujme nejprve strukturu Cas, která má tři soukromé celočíselné datové složky hodiny, minuty, sekundy. Struktura obsahuje konstruktor, který inicializuje hodnoty všech datový složek pomocí formálních parametrů hodiny, minuty, sekundy – viz Kód 3.

//Deklarace datového typu struktura
struct Cas
{
    //Deklarace celočíselných datových složek
    private int hodiny, minuty, sekundy;
 
    //Deklarace konstruktoru
    public Cas(int hodiny, int minuty, int sekundy)
    {
        //Přiřazení hodnot celočíselným datovým složkám
        this.hodiny = hodiny;
        this.minuty = minuty;
        this.sekundy = sekundy;
    }
}

Kód 3: Deklarace struktury Cas včetně inicializace jejích datových složek v konstruktoru

V metodě Main vytvoříme dva prvky pole s názvem poleStruktur obsahující jednotlivé struktury Cas . Jednotlivé struktury byly vytvořeny zavoláním konstruktorů struktury Cas, které jsou uzavřeny do složených závorek ve výrazu - viz Kód 4. Těmto konstruktorům jsou předány skutečné parametry definované v kulatých závorkách u každého konstruktoru.

//Vytvoření pole struktur Cas včetně jejich inicializace
Cas[] poleStruktur = { new Cas(12, 30, 50), new Cas(5, 30, 6) };

Kód 4: Příklad vytvoření instance poleStruktur včetně zavolání konstruktoru Cas pro jednotlivé struktury

5. Implicitně typovaná pole

Jak již bylo řečeno, typ pole uváděný v deklaraci se musí shodovat s datovým typem jednotlivých prvků pole. Další možností je nechat kompilátor si odvodit datový typ prvků pole ze seznamu inicializátoru uvedených ve složené závorce. Obecná syntaxe takového zápisu pro jednorozměrné pole:

var identifikátorPole = new [ ] {seznamInicializátorů}

kde:

  • var - klíčové slovo identifikující, že jde o typ implicitně typovaného pole
  • identifikátorPole - definuje název jednorozměrného pole
  • new - klíčové slovo vytvářející instanci pole
  • seznamInicializátorů - představuje seznam jednotlivých hodnot prvků pole


Ilustrativní příklad ImplicitneTypovanePoleJmen
Program ImplicitneTypovanePoleJmen
  • Popis: Vytvoření jednorozměrného implicitně typovaného pole s datovým typem string
  • Zadání: Zkuste deklarovat implicitně typované pole obsahující jména: "Petr", "Jan", "Pavel", "Zdeněk"
  • Řešení: Bude postupně probráno v následujícím textu


V následujícím kódu vidíme, že datový typ uváděný v předchozích příkladech byl nahrazen klíčovým slovem var, které uvozuje identifikátor proměnné – viz Kód 1. Dále byly v zápisu také vynechány závorky uvozující název pole. Datový typ si kompilátor odvodil ze seznamu jednotlivých inicializátoru – textových řetězců (tedy typ string) uzavřených ve složené závorce, které představují jednotlivé prvky pole. 

//Vytvoření instance implicitně typovaného pole včetně jeho inicializace
var jmena = new[] { "Petr", "Jan", "Pavel", "Zdeněk" };

Kód 1: Příklad vytvoření instance jednorozměrného implicitně typovaného pole

Je důležité zajistit, aby všechny inicializátory byly stejného datového typu, jinak kompilátor nahlásí chybu: Nebyl nalezen optimální typ pro implicitně typované pole. Tento přístup se používá zejména u objektů anonymní třídy, kde jsou inicializovány jednotlivé datové složky takových instancí.


Ilustrativní příklad ImplicitneTypovanePoleLidi
Program ImplicitneTypovanePoleLidi
  • Popis: Vytvoření jednorozměrného implicitně typovaného pole s instancemi anonymní třídy
  • Zadání: Zkuste deklarovat implicitně typované pole nazvané lide. Jednotlivé prvky pole jsou instancemi anonymní třídy. Třída obsahuje datové složky:
    • Jmeno – jméno člověka (datový typ string). Jednotlivá jména: "Petr", "Jan", "Pavel", "Zdeněk"
    • Vek – věk člověka (datový typ int). Věk lidí: 39, 67, 38, 45
  • Řešení: Bude postupně probráno v následujícím textu


V následujícím kódu vidíme, že deklarace implicitně typovaného pole je stejná jako v předchozím příkladu – viz Kód 2. Rozdíl je ve výrazu napravo od přiřazení, kde konstruktor pole využívá další konstruktory anonymní třídy pro generování instancí této třídy. U konstruktoru každé instance pak stačí do složených závorek (značící identifikátory) doplnit hodnoty jednotlivých datových složek.

//Vytvoření instance implicitně typovaného pole s instancemi anonymní třídy
var lide = new[] { new { Jmeno = "Petr", Vek = 39 },
                    new { Jmeno = "Jan", Vek = 67 },
                    new { Jmeno = "Pavel", Vek = 38 },
                    new { Jmeno = "Zdeněk", Vek = 45 } };

Kód 2: Příklad vytvoření instance jednorozměrného implicitně typovaného pole obsahující instance anonymní třídy


6. Přístup k prvkům pole

Pro ilustraci principu procházení prvků pole využijme předchozí příklad deklarace jednorozměrného pole včetně inicializace jeho prvků s odvozením velikosti pole pomocí kompilátoru – viz Kód 1. Jednalo se o deklaraci jednorozměrného pole obsahující celá čísla, včetně vytvoření instance takového pole o 5 prvcích: 7, 5, 2, 4, 9. Instance se jmenovala poctyLidi. 

/*Vytvoření instance pole o 5 prvcích včetně inicializace, kde
*velikost pole je odvozena kompilátorem */
int[] poctyLidi = { 7, 5, 2, 4, 9 };

Kód 1: Příklad deklarace jednorozměrného pole poctyLidi s odvozením velikosti pole, vytvoření instance včetně inicializace

Na obrázku vidíme, co by provedl předchozí kód v paměti - viz Obrázek 1.

Deklarace jednorozměrného pole poctyLidi včetně inicializace

Obrázek 1: Deklarace jednorozměrného pole poctyLidi včetně inicializace

Pro procházení prvků jednorozměrného pole je zapotřebí pouze jeden index, pomocí kterého přistupujeme k jednotlivým prvkům tohoto pole, jak je vidět u jednotlivých prvků pole na obrázku – viz Obrázek 2. První prvek má hodnotu indexu 0, další 1 (o jedna vyšší než předchozí), atd.

Přístup k jednotlivým prvkům pole poctyLidi

Obrázek 2: Přístup k jednotlivým prvkům pole poctyLidi


Ilustrativní příklad PoleLidiVypisPrvku
Program PoleLidiVypisPrvku
  • Popis: Výpis obsahu předposledního prvku jednorozměrného pole obsahující celá čísla
  • Zadání: Vytvořte instanci jednorozměrného celočíselného pole o 5 prvcích: 7, 5, 2, 4, 9. Instance se bude jmenovat poctyLidi. Vypište v metodě Main hodnotu předposledního prvku instance poctyLidi
  • Řešení: Bude postupně probráno v následujícím textu


Pro výpis v konzolové aplikaci jsme použili standardní příkaz WriteLine, kde jsme v závorce zobrazili informaci o pozici prvku (je důležité si uvědomit, že první prvek pole má index 0 a proto index předposledního prvku je 3) – viz Kód 2.
static void Main(string[] args)
{
    /*Vytvoření instance pole o 5 prvcích včetně inicializace, kde
    *velikost pole je odvozena kompilátorem */
    int[] poctyLidi = { 7, 5, 2, 4, 9 };
 
    //Výpis hodnoty předposledního prvku jednorozměrného pole
    Console.WriteLine("Prvek na pozici {0} má hodnotu: {1}", 3, poctyLidi[3]);
 
 
    //Čekání na stisk klávesy -> ukončení programu
    Console.ReadKey();
}

Kód 2: Výpis obsahu předposledního prvku jednorozměrného pole poctyLidi obsahující celá čísla

Na výpisu v konzoli vidíme, že byla vypsána indexu prvku včetně jeho hodnoty – viz Výstup programu - Kód 2.

Prvek na pozici 3 má hodnotu: 4

Výstup programu - Kód 2: Výpis obsahu předposledního prvku jednorozměrného pole poctyLidi obsahující celá čísla


Zkusme si vytvořit program, kde uživatel bude zadávat index prvku sám. Uživatel je tvor lidský, tudíž může udělat chybu. Zkusme pomocí výjimky ošetřit program proti chybě na straně uživatele.


Ilustrativní příklad PoleLidiVypisVyjimka
Program PoleLidiVypisVyjimka
  • Popis: Výpis obsahu prvku jednorozměrného pole obsahujícího celá čísla s testem konverze a ošetřením výjimky
  • Zadání: Vytvořte instanci jednorozměrného celočíselného pole o 5 prvcích: 7, 5, 2, 4, 9. Instance se bude jmenovat poctyLidi. Vypište hodnotu prvku instance poctyLidi, kde index prvku bude načten od uživatele. Pokud uživatel zadá špatný číselný formát indexu, vypište mu varovné hlášení: "Zadal jste špatný formát čísla indexu". Pokud bude index mimo povolené hranice, vypište uživateli text vyvolané výjimky typu IndexOutOfRangeException
  • Řešení: PoleLidiVypisVyjimka_Main


V následujícím výřezu kódu našeho programu nejprve vybídneme uživatele, aby zadal index prvku – viz Kód 3. Je vhodné uživatele přímo informovat o hodnotách, které může zadávat. Proto jsme v závorkách příkazu Write (tento příkaz nezařádkuje na další řádek) využili vlastnost Length, která navrací hodnotu velikosti pole. U vlastnosti Length se nemusí používat závorka, protože to není metoda! Vzhledem k tomu, že první index má hodnotu 0, museli jsme odečíst hodnotu 1 od velikosti pole, abychom získali index posledního prvku. Pro konverzi zadaných číslic na hodnotu celého čísla, jsme využili příkaz TryParse. Tento příkaz kromě konverze také umí vyhodnotit, zda lze provést konverzi. Pokud ano, navrátí hodnotu true a hodnota výstupního parametr je uložena do lokální proměnné indexPrvku. V kladné větvi příkazu if, tzn., že proběhla konverze číslic, je v bloku try ošetřen potenciálně nebezpečný kód na zadání chybné hodnoty indexu ze strany uživatele. Pokud uživatel zadá špatnou hodnotu indexu prvku, je vyvolána výjimka typu IndexOutOfRangeException a v bloku příkazu catch je provedeno ošetření této výjimky. Pokud uživatel zadal správný index prvku, je vypsána hodnota prvku na pozici indexPrvku. Pokud neproběhla konverze číslic na hodnotu, která lze uložit do proměnné indexPrvku, bude vykonán výpis v záporné větvi příkazu if. V tomto výpis bude zobrazena chyba, která vyvolala výjimku.


//Výpis textu pro zadání indexu
Console.Write("Zadejte index prvku pole(0÷{0}): ", poctyLidi.Length - 1);
/*Test, zda proběhne konverze zadaného textu na číslo, pokud proběhla
 * konverze bude hodnota uložena do proměnné indexPrvku*/
if (int.TryParse(Console.ReadLine(), out int indexPrvku) == true)
    //Potenciálně nebezpečný kód na chybně zadaný index
    try
    {
        //Výpis hodnoty prvku jednorozměrného pole na základě načteného indexu
        Console.WriteLine("Prvek na pozici {0} má hodnotu: {1}",
            indexPrvku, poctyLidi[indexPrvku]);
    }
    //Ošetření výjimky
    catch (IndexOutOfRangeException ex)
    {
        Console.WriteLine("Nastala výjimka: {0}", ex.ToString());
    }
//Neproběhla konverze - chybně zadaný index
else
{
    Console.WriteLine("Zadal jste špatný formát čísla indexu");
    return;
}

Kód 3: Výpis obsahu prvku jednorozměrného pole poctyLidi s testem konverze a ošetřením výjimky

Na výpisu v konzoli vidíme zadání indexu 1 (tzn. druhý prvek pole) a následný výpis hodnoty prvku na specifikované pozici – viz Výstup programu 1 - PoleLidiVypisVyjimka_Main.

Zadejte index prvku pole(0÷4): 1
Prvek na pozici 1 má hodnotu: 5

Výstup programu 1 - PoleLidiVypisVyjimka_Main: Ukázka výpisu hodnoty prvku na specifikované pozici 

Zkusme zadat namísto čísla indexu text, který nelze konvertovat. Jak vidíme, příkaz TryParse nedokáže tento text konvertovat na celé číslo a je vykonán výpis varovného hlášení uživateli a metoda Main je ukončena – viz Výstup programu 2.

Zadejte index prvku pole(0÷4): bflm
Zadal jste špatný formát čísla indexu

Výstup programu 2 - PoleLidiVypisVyjimka_Main: Ukázka zadání textu namísto indexu prvku

Při pokusu zadat index prvku, mimo rozsah povolených mezí nastane ošetření výjimky a v konzoli je vypsán text uložený ve výjimce, který specifikuje příčinu chyby – viz Výstup programu 3.

Zadejte index prvku pole(0÷4): 5
Nastala výjimka: System.IndexOutOfRangeException: Index was outside the bounds of the array.

Výstup programu 3 - PoleLidiVypisVyjimka_Main: Ukázka výpisu výjimky při neplatném indexu prvku pole


Ilustrativní příklad PoleStrukturCas
Program PoleStrukturCas
  • Popis: Deklarace jednorozměrného pole obsahující jednotlivé struktury
  • Zadání: Zkuste deklarovat pole struktur, které bude obsahovat prvky, které obsahují strukturu Cas. Jednotlivé struktury jsou inicializovány vlastním konstruktorem. Struktura bude obsahovat tři celočíselné datové složky (datový typ int):
    • hodiny – počet hodin
    • minuty – počet minut
    • sekundy – počet sekund

      Konstruktor struktury bude přijímat tři formální parametry: hodiny, minuty, sekundy. Pomocí hodnot těchto parametrů nastavte datové složky struktury Cas. Vytvořte v metodě Main pole struktur poleStruktur obsahující dva prvky struktury Cas vytvořených pomocí zavolání konstruktoru struktury. Inicializujte první prvek (struktury) pole hodnotami: 12, 30, 50 a druhý prvek: 5, 30, 6. Vypište pomocí metod implementovaných ve struktuře VratHodiny, VratMinuty, VratSekundy časové hodnoty u obou prvků typu struktura Cas umístěných v poli
  • Řešení: PoleStrukturCas_Main

Následující příklad rozvíjí předchozí příklad PoleStrukturInicilazace, kde jsme vytvořili pole struktur pomocí volání konstruktoru u jednotlivých prvků, tzn. jednotlivých struktur. Jako první jsme deklarovali strukturu Cas, která má tři soukromé celočíselné datové složky hodiny, minuty, sekundy. Struktura obsahovala konstruktor, který inicializuje hodnoty všech datový složek pomocí formálních parametrů hodiny, minuty, sekundy – viz Kód 4.

//Deklarace datového typu struktura
struct Cas
{
    //Deklarace celočíselných datových složek
    private int hodiny, minuty, sekundy;
 
    //Deklarace konstruktoru
    public Cas(int hodiny, int minuty, int sekundy)
    {
        //Přiřazení hodnot celočíselným datovým složkám
        this.hodiny = hodiny;
        this.minuty = minuty;
        this.sekundy = sekundy;
    }
}

Kód 4: Deklarace struktury Cas včetně inicializace jejích datových složek v konstruktoru

Pro obdržení hodnoty uložené v datové složce např. hodiny, vytvoříme metodu VratHodiny, která nám navrací celočíselnou hodnotu počtu hodin (hodiny jsou datového typu int). Tato metoda je volně přístupná i mimo strukturu - přístupový modifikátor public. Tato metoda nemá žádný vstupní parametr, protože pouze potřebujeme získat výstup, tj. hodnotu příslušné datové složky. K té přistoupíme pomocí tečkové notace s využitím this. Pro přiřazení výstupu této metody využijeme příkaz return - viz Kód 5. Stejným způsobem budeme postupovat u dalších datových složek minuty a sekundy.

//Deklarace metody ve struktuře - navrací hodnotu datové složky 'hodiny'
public int VratHodiny()
{
    //Navrácení hodnoty datové složky
    return this.hodiny;
}

Kód 5: Deklarace metody VratHodiny - navrácení hodnoty datové složky

V metodě Main vytvoříme dva prvky pole s názvem poleStruktur obsahující jednotlivé struktury Cas . Jednotlivé struktury byly vytvořeny zavoláním konstruktorů struktury Cas, které jsou uzavřeny do složených závorek ve výrazu - viz Kód 6. Těmto konstruktorům jsou předány skutečné parametry definované v kulatých závorkách u každého konstruktoru.

//Vytvoření pole struktur Cas včetně jejich inicializace
Cas[] poleStruktur = { new Cas(12, 30, 50), new Cas(5, 30, 6) };

Kód 6: Příklad vytvoření instance poleStruktur včetně zavolání konstruktoru Cas pro jednotlivé struktury

Pro přístup k jednotlivým strukturám uložených jako prvky pole využijeme indexu v hranatých závorkách. K prvnímu prvku pole poleStuktur (tj. první instanci struktury Cas) přistoupíme pomocí indexu 0 uzavřeného v hranatých závorkách, tj. poleStuktur[0]. U každé instance necháme pomocí metod VratHodiny, VratMinuty, VratSekundy necháme vypsat hodnoty jednotlivých datových složek struktury - viz Kód 7.

/* Výpis jednotlivých hodnot v datových složkách první struktury uložené v prvním 
 * prvku pole (index 0) */ 
Console.WriteLine("První instance času: {0} hodin, {1} minut, {2} sekund", 
    poleStruktur[0].VratHodiny(), poleStruktur[0].VratMinuty(), poleStruktur[0].VratSekundy());

Kód 7: Výpis datových složek první instance uložené v prvním prvku pole struktur pomocí metod struktury

Na výpisu vidíme, jaké jsou hodnoty jednotlivých datových složek struktur uložených ve dvou prvcích pole - viz Výstup programu - PoleStrukturCas_Main.

První instance času: 12 hodin, 30 minut, 50 sekund
Druhá instance času: 5 hodin, 30 minut, 6 sekund

Výstup programu - PoleStrukturCas_Main: Ukázka výpisu obsahu datových složek struktur uložených v prvcích pole

7. Procházení prvků pole pomocí cyklu

Všechna pole jsou ve skutečnosti instancemi třídy System.Array prostředí .NET Framework. Tato třída definuje některé užitečné vlastnosti a metody. Můžeme se dotázat na vlastnost Length pro zjištění počtu prvků v poli a lze také procházet všechny prvky matice pomocí příkazu for.

C# poskytuje další možnost procházet prvky pole pomocí příkazu foreach, kde není zapotřebí používat indexy.

Příkaz foreach deklaruje řídící (iterační) proměnnou cyklu, která automaticky získá hodnotu každého prvku v poli. Typ této proměnné musí odpovídat typu prvků v poli. Příkaz foreach je preferovaný způsob procházení prvků pole, který přímo vyjadřuje záměr kódu procházet všechny prvky pole. V několika případech však zjistíte, že se musíte vrátit zpět k příkazu for:

  • Příkaz foreach vždy prochází celé pole. Pokud chceme procházet pouze část pole (například první polovinu), nebo se vyhnout určitým prvkům (například každý třetí prvek), je jednodušší použít příkaz for
  • Příkaz foreach vždy probíhá od indexu 0 do délky pole - 1. Pokud chceme procházet prvky odzadu nebo v jiné sekvenci, je jednodušší použít příkaz for
  • Pokud potřebujeme znát uvnitř tělo cyklu index prvku, nikoli pouze hodnotu prvku, musíme použít příkaz for
  • Pokud potřebujeme upravit prvky pole, musíme použít příkaz for. Důvodem je to, že řídící proměnná cyklu foreach je kopií každého prvku pole, kterou lze použít pouze pro čtení [6]


Ilustrativní příklad PoleLidiVypisFor
Program PoleLidiVypisFor
  • Popis: Výpis obsahu všech prvků jednorozměrného pole obsahující celá čísla pomocí cyklu s krokem
  • Zadání: Vytvořte instanci jednorozměrného celočíselného pole o 5 prvcích: 7, 5, 2, 4, 9. Instance se bude jmenovat poctyLidi. Vypište v metodě Main hodnoty všech prvků instance poctyLidi pomocí cyklu s krokem
  • Řešení: Bude postupně probráno v následujícím textu


Pro výpis všech prvků je vhodné použít cyklus for, poněvadž víme, že proběhne tolik iterací s příkazem výpisu obsahu prvku, kolik je prvků v poli. Proto jsme využili v podmínce cyklu vlastnost Length, která nám vrací počet prvků, v našem případě jednorozměrného pole. Postačí nám tedy pouze jeden čítač (proměnná indexPrvku) – viz Kód 1.

static void Main(string[] args)
{
    //Vytvoření instance pole o 5 prvcích včetně inicializace
    int[] poctyLidi = { 7, 5, 2, 4, 9 };
 
    //Cyklus s krokem pro procházení prvků pole
    for (int indexPrvku = 0; indexPrvku < poctyLidi.Length; indexPrvku++)
    {
        //Výpis hodnoty prvku jednorozměrného pole na základě indexu
        Console.WriteLine("Prvek na pozici {0} má hodnotu: {1}",
            indexPrvku, poctyLidi[indexPrvku]);
    }
 
    //Čekání na stisk klávesy -> ukončení programu
    Console.ReadKey();
}

Kód 1: Výpis obsahu prvků jednorozměrného pole poctyLidi obsahujícího celá čísla včetně pozic prvků

Na výpisu v konzoli vidíme výpis pozic a obsahu prvků jednorozměrného pole – viz Výstup programu - Kód 1.

Prvek na pozici 0 má hodnotu: 7
Prvek na pozici 1 má hodnotu: 5
Prvek na pozici 2 má hodnotu: 2
Prvek na pozici 3 má hodnotu: 4
Prvek na pozici 4 má hodnotu: 9

Výstup programu - Kód 1: Příklad výpisu obsahu prvků jednorozměrného pole včetně pozic prvků


Ilustrativní příklad PoleLidiVypisForeach
Program PoleLidiVypisForeach
  • Popis: Výpis obsahu všech prvků jednorozměrného pole obsahující celá čísla pomocí cyklu foreach
  • Zadání: Vytvořte instanci jednorozměrného celočíselného pole o 5 prvcích: 7, 5, 2, 4, 9. Instance se bude jmenovat poctyLidi. Vypište v metodě Main hodnoty všech prvků instance poctyLidi pomocí cyklu foreach
  • Řešení: Bude postupně probráno v následujícím textu

Výhoda cyklu foreach je na rozdíl od cyklu for v úspoře kódu (za podmínek že nepotřebujeme vypisovat aktuální indexy prvků). V cyklu je definován stejný datový typ int řídící proměnné, jako je datový typ prvků pole. Do této proměnné je uložena hodnota aktuálního prvku. Tuto proměnnou jsme pojmenovali pocet. Obsah tohoto prvku následně využíváme v těle cyklu při výpisu WriteLine – viz Kód 2.

static void Main(string[] args)
{
    //Vytvoření instance pole o 5 prvcích včetně inicializace
    int[] poctyLidi = { 7, 5, 2, 4, 9 };
 
    //Cyklus s krokem pro procházení prvků pole
    foreach (int pocet in poctyLidi)
    {
        //Výpis hodnoty prvku jednorozměrného pole
        Console.WriteLine("Prvek má hodnotu: {0}", pocet);
    }
 
    //Čekání na stisk klávesy -> ukončení programu
    Console.ReadKey();
}

Kód 2: Výpis obsahu prvků jednorozměrného pole poctyLidi obsahujícího celá čísla bez pozic prvků

Na výpisu v konzoli vidíme pouze výpis obsahu prvků jednorozměrného pole – viz Výstup programu - Kód 2.

Prvek má hodnotu: 7
Prvek má hodnotu: 5
Prvek má hodnotu: 2
Prvek má hodnotu: 4
Prvek má hodnotu: 9

Výstup programu - Kód 2: Příklad výpisu obsahu prvků jednorozměrného pole bez pozic prvků


Využijme předchozího příkladu deklarace implicitně typovaného jednorozměrného pole nazvané lide s instancemi anonymní třídy – viz ilustrativní příklad ImplicitneTypovanePoleLidi v kapitole Implicitně typovaná pole. 


Ilustrativní příklad ImplicitneTypovanePoleLidiVypis
Program ImplicitneTypovanePoleLidiVypis
  • Popis: Vytvoření jednorozměrného implicitně typovaného pole s instancemi anonymní třídy, výpis obsahu prvků pole
  • Zadání: Deklarujte implicitně typované pole nazvané lide. Jednotlivé prvky pole jsou instancemi anonymní třídy. Třída obsahuje datové složky:
    • Jmeno – jméno člověka (datový typ string). Jednotlivá jména: "Petr", "Jan", "Pavel", "Zdeněk"
    • Vek – věk člověka (datový typ int). Věk lidí: 39, 67, 38, 45

V metodě Main vypište hodnoty všech prvků instance lide pomocí cyklu foreach. Řídící proměnnou tohoto cyklu nazvěte clovek

  • Řešení: Bude postupně probráno v následujícím textu

Jednotlivé prvky pole jsou instancemi anonymní třídy, která obsahuje datové složky Jmeno a Vek. V cyklu foreach pro procházení jednotlivých prvků implicitně typovaného pole lide je deklarována implicitně typovaná proměnná řídícího cyklu nazvaná clovek, v níž je uložena hodnota aktuálního prvku, tj. právě procházená instance anonymní třídy. V této instanci jsou uloženy hodnoty datových složek. Jednotlivé hodnoty datových složek (k nimž přistupujeme pomocí tečkové notace u deklarované instance anonymní třídy) jsou vypisovány pomocí příkazu WriteLine – viz Kód 3.

static void Main(string[] args)
{
    //Vytvoření instance implicitně typovaného pole s instancemi anonymní třídy
    var lide = new[] { new { Jmeno = "Petr", Vek = 39 },
                        new { Jmeno = "Jan", Vek = 67 },
                        new { Jmeno = "Pavel", Vek = 38 },
                        new { Jmeno = "Zdeněk", Vek = 45 } };
 
    //Cyklus s krokem pro procházení prvků implicitně typovaného pole
    foreach (var clovek in lide)
    {
        //Výpis hodnoty prvku jednorozměrného pole
        Console.WriteLine("Jméno: {0}, věk: {1}", clovek.Jmeno, clovek.Vek);
    }
 
    //Čekání na stisk klávesy -> ukončení programu
    Console.ReadKey();
}

Kód 3: Výpis obsahu datových složek instancí anonymní třídy umístěných v jednorozměrném poli

Na výpisu v konzoli vidíme výpis datových složek prvků jednorozměrného pole. Tyto prvky jsou tvořeny instancemi třídy lide – viz Výstup programu - Kód 3.

Jméno: Petr, věk: 39
Jméno: Jan, věk: 67
Jméno: Pavel, věk: 38
Jméno: Zdeněk, věk: 45

Výstup programu - Kód 3: Výpis obsahu datových složek instancí anonymní třídy umístěných v jednorozměrném poli

8. Předání pole jako parametru, nebo jako návratu metody

V C# lze definovat metody, které přijímají pole jako parametry, nebo je navrací zpět. Syntaxe pro předávání pole jako parametru je téměř totožná s deklarací pole.

Asi jste si všimli, že hlavní metoda aplikace přijímá jako argument (parametr) pole řetězců: 

static void Main (string [] args){ … }

Nezapomeňme, že hlavní metoda je volána při spuštění programu; je to tedy vstupní bod vaší aplikace. Pokud spustíme aplikaci z příkazového řádku, můžeme zadat argumenty této metody pomocí příkazového řádku. Operační systém Windows předá tyto argumenty do interpreteru (CLR - Common Language Runtime), který je předá jako argumenty hlavní metodě. Tento mechanismus nám poskytuje jednoduchý způsob, jak umožnit uživateli zadat informace při spuštění aplikace namísto interaktivního vyzývání uživatele. Tento přístup je užitečný, pokud chceme vytvářet nástroje, které lze spouštět z automatizovaných skriptů.

Příklad následujícího kódu, definuje metodu pojmenovanou ZpracujData, která přijímá jednorozměrné pole celých čísel (formální parametr) – viz Kód 1. V těle metody jsou procházeny prvky pole pomocí cyklu foreach a u každého prvku se provádí jeho nespecifikované zpracování. [6]

//Deklarace metody přijímací jednorozměrné pole 
public void ZpracujData(int[] data)
{
    //Cyklus procházející jednotlivá data
    foreach (int i in data)
    {
        //...zpracování dat
    }
}

Kód 1: Příklad metody přijímací jednorozměrné pole jako formální parametr

Je důležité si uvědomit, že pole jsou referenčního typu, takže pokud změníme uvnitř metody obsah pole předaného jako parametr, změna se promítne i vně této metody.

Pokud potřebujeme pole uvnitř metody vytvořit, případně naplnit atd., můžeme pole deklarovat jako návratový typ, nebo jako návrat metody.


Ilustrativní příklad VytvorPole
Program VytvorPole
  • Popis: Deklarace metody pro vytvoření jednorozměrného pole včetně naplnění obsahu prvků
  • Zadání: Vytvořte metodu VytvorPole, která vytvoří instanci jednorozměrného pole nazvanou pole o načtené velikosti velikostPole definující počet celočíselných prvků pole. Instance pole bude deklarována jako návrat metody. Uživatel naplní obsah všech prvků pole pomocí klávesnice. Metodu zavolejte v metodě Main
  • Řešení: Bude postupně probráno v následujícím textu


Jak vidíme, v deklaraci metody jsme uvedli, že metoda je statická (budeme jí volat v metodě Main) a veřejná – viz Kód 2. Návratový typ této metody je jednorozměrné pole celých čísel. V těle metody vybídneme uživatele k zadání velikosti pole, tedy počtu prvků pole. Po načtení a konverzi velikosti pole je vytvořena instance jednorozměrného pole o specifikované velikosti. Uvnitř těla jsme definovali cyklus s krokem, protože chceme uživatele informovat, o pořadí prvku, který zadává. K informaci o pořadí prvku jsme použili řídící proměnnou cyklu. Tuto hodnotu jsme zvýšili o 1, poněvadž by bylo nevhodné psát u prvního prvku pole "Zadejte hodnotu 0. prvku: ". Načtenou hodnotu od uživatele jsme uložili do prvku pole na aktuální pozici určenou pomocí indexu i. Výstupem metody je vytvořená a naplněná instance jednorozměrného pole.

//Deklarace metody navracející jednorozměrné pole
public static int[] VytvorPole()
{
    //Výpis textu pro zadání počtu prvků pole, tj. velikost pole
    Console.Write("Zadejte počet prvků pole: ");
    //Konverze zadaného textu na číslo
    int velikostPole = int.Parse(Console.ReadLine());
    //Vytvoření instance jednorozměného pole o specifikované velikosti
    int[] pole = new int[velikostPole];
    //Cyklus procházející jednotlivé prvky
    for (int i = 0; i < velikostPole; i++)
    {
        //Výpis textu pro zadání obsahu prvku pole
        Console.Write("Zadejte hodnotu {0}.prvku: ", i + 1);
        //Přiřazení načtené hodnoty prvku
        pole[i] = int.Parse(Console.ReadLine());
    }
    //Výstup metody je jednorozměrné pole
    return pole;
}

Kód 2: Deklarace metody VytvorPole pro vytvoření jednorozměrného pole včetně naplnění obsahu prvků

V následujícím kódu těla statické metody Main vidíme volání metody VytvorPole – viz Kód 3.

static void Main(string[] args)
{
    //Vytvoření instance jednorozměrného pole a naplnění prvků
    int[] pole = VytvorPole();
}

Kód 3: Volání metody pro vytvoření jednorozměrného pole včetně naplnění obsahu prvků ve statické metodě Main

Výpis v konzoli ukazuje zadání velikosti pole a následné zadání hodnot jednorozměrného pole pomocí metody VytvorPole – viz Výstup programu - Kód 3.

Zadejte počet prvků pole: 5
Zadejte hodnotu 1.prvku: 0
Zadejte hodnotu 2.prvku: 1
Zadejte hodnotu 3.prvku: 2
Zadejte hodnotu 4.prvku: 3
Zadejte hodnotu 5.prvku: 4

Výstup programu - Kód 3: Příklad vytvoření jednorozměrného pole včetně naplnění obsahu prvků


Využijme těla předchozího příkladu pro vytvoření instance jednorozměrného pole a zkusme si deklarovat pole jako výstupní parametr metody.


Ilustrativní příklad VytvorPolePretizeni
Program VytvorPolePretizeni
  • Popis: Deklarace přetížené metody pro vytvoření jednorozměrného pole předaného jako výstupní parametr metody (včetně naplnění obsahu prvků)
  • Zadání: Využijte předchozí tělo metody VytvorPole a vytvořte přetíženou metodu VytvorPole, s tím rozdílem, že instance jednorozměrného pole bude deklarována jako výstupní parametr metody. Metodu zavolejte v metodě Main
  • Řešení: Bude postupně probráno v následujícím textu

Hlavním rozdílem oproti předchozí metodě je ve způsobu deklarace metody – viz Kód 4. Návratový typ této statické metody je void a předání instance jednorozměrného pole je realizováno pomocí deklarace výstupního parametru pomocí klíčového slova out. Za tímto klíčovým slovem následuje deklarace jednorozměrného pole celých čísel včetně specifikace názvu tohoto pole. Díky tomu nemusíme uvádět uvnitř těla metody deklarace jednorozměrného pole jako lokální proměnné a při vytváření instance pouze  stačí použít název tohoto výstupní parametru, tedy pole. Dále není zapotřebí navracet výstup, tzn., že byla smazána řádka s klíčovým slovem return.

//Deklarace metody, kde jednorozměrné pole je deklarováno jako výstupní parametr metody
public static void VytvorPole(out int[] pole)
{
    //Výpis textu pro zadání počtu prvků pole, tj. velikost pole
    Console.Write("Zadejte počet prvků pole: ");
    //Konverze zadaného textu na číslo
    int velikostPole = int.Parse(Console.ReadLine());
    //Vytvoření instance jednorozměrného pole o specifikované velikosti
    pole = new int[velikostPole];
    //Cyklus procházející jednotlivé prvky
    for (int i = 0; i < velikostPole; i++)
    {
        //Výpis textu pro zadání obsahu prvku pole
        Console.Write("Zadejte hodnotu {0}.prvku: ", i + 1);
        //Přiřazení načtené hodnoty prvku
        pole[i] = int.Parse(Console.ReadLine());
    }
}

Kód 4: Deklarace přetížené metody VytvorPole pro vytvoření jednorozměrného pole předaného jako výstupní parametr metody

V následujícím kódu těla statické metody Main vidíme rozdíl ve volání přetížené metody VytvorPole (předchozí volání metody s návratem je okomentované - zelené). Ve volání metody jsme v závorce deklarovali typ jednorozměrného pole a instance bude vytvořena a naplněna v deklarované metodě – viz Kód 5.

static void Main(string[] args)
{
    ////Vytvoření instance jednorozměrného pole a naplnění prvků pomocí metody s návratem
    //int[] pole = VytvorPole();
 
    //Volání přetížené metody, kde jednorozměrné pole je výstupní parametr metody
    VytvorPole(out int[] pole);
}

Kód 5:  Volání přetížené metody VytvorPole pro vytvoření jednorozměrného pole předaného jako výstupní parametr metody ve statické metodě Main

Vzhledem k tomu, že jednorozměrné pole již máme vytvořeno, měli bychom se pokusit jeho obsah.


Ilustrativní příklad VytvorVypisPole
Program VytvorVypisPole
  • Popis: Metoda pro výpis obsahů všech celočíselných prvků jednorozměrného pole
  • Zadání: Deklarujte metodu bez návratu VypisPole, která vypíše hodnoty všech celočíselných prvků instance jednorozměrného pole nazvané pole, která byla vytvořena pomocí metody VytvorPole. Vypište také pořadí jednotlivých prvků. Metodu zavolejte v metodě Main
  • Řešení: VytvorVypisPole_Main

Deklarovaná metoda přijímá jednorozměrné pole celočíselných prvků a nemá žádný návrat (potřebujeme jen vypsat hodnoty v prvcích pole), proto v deklaraci uvedeme slovo jako návratový datový typ metody void – viz Kód 6. Uvnitř těla metody je použit cyklus for, vzhledem k tomu, že víme, kolik prvků obsahuje a také kvůli tomu, že u jednotlivých prvků chceme uvádět jejich pořadí v poli (proto jsme nevyužili cyklus foreach). Hodnotu pořadí zjišťujeme z hodnoty řídící proměnné cyklu, ke které přičítáme 1 (nechceme, aby pořadí prvního prvku bylo vypsáno jako nulté). Délku pole, kterou je nutné uvést uvnitř cyklu, zjistíme pomocí vlastnosti Length.

//Deklarace metody vypisující obsah všech prvků jednorozměrného pole
public static void VypisPole(int[] pole)
{
    //Cyklus procházející jednotlivé prvky
    for (int i = 0; i < pole.Length; i++)
    {
        //Výpis textu pro zadání obsahu prvku pole včetně pořadí prvku
        Console.WriteLine("Hodnota {0}.prvku: {1}", i+1, pole[i]);
    }
}

Kód 6: Deklarace metody VypisPole pro výpis obsahů všech celočíselných prvků jednorozměrného pole

V následujícím kódu těla statické metody Main vidíme volání metody VypisPole. Ve volání metody jsme v závorce předali instanci jednorozměrného pole, která bude v deklarované metodě vypsána – viz Kód 7.

//Zavolání metody pro vypsání obsahů prvků pole
VypisPole(pole);

Kód 7: Volání metody pro výpis obsahů všech celočíselných prvků jednorozměrného pole ve statické metodě Main

V konzoli vidíme hodnoty jednotlivých celočíselných prvků uvnitř instance jednorozměrného pole s názvem pole – viz Výstup programu - VytvorVypisPole_Main.

Zadejte počet prvků pole: 5
Zadejte hodnotu 1.prvku: 1
Zadejte hodnotu 2.prvku: 2
Zadejte hodnotu 3.prvku: 3
Zadejte hodnotu 4.prvku: 4
Zadejte hodnotu 5.prvku: 5
Hodnota 1.prvku: 1
Hodnota 2.prvku: 2
Hodnota 3.prvku: 3
Hodnota 4.prvku: 4
Hodnota 5.prvku: 5

Výstup programu - VytvorVypisPole_Main: Příklad výpisu obsahů všech vytvořených celočíselných prvků jednorozměrného pole

9. Kopírování pole

Pole jsou referenční typy, tzn., že pokud je vytvořena instance typu pole (tj. instance třídy System.Array), proměnná se odkazuje na místo v paměti (haldě), kde jsou uloženy jednotlivé prvky tohoto pole. Pokud tedy přiřazujeme proměnné proměnnou, nevytváříme kopii proměnné, ale přiřazujeme odkaz na tentýž blok paměti, na který odkazuje kopírovaná proměnná, jak popisuje následující příklad – viz Kód 1 (využijme předchozí příklad deklarace jednorozměrného pole včetně inicializace jeho prvků s odvozením velikosti pole pomocí kompilátoru).

static void Main(string[] args)
{
    //Vytvoření instance pole o 5 prvcích včetně inicializace
    int[] poctyLidi = { 7, 5, 2, 4, 9 };
    /*Nevytvoří se kopie pole, ale vytváříme referenci na stejný blok paměti, 
     * kterou využívá pole(instance) poctyLidi*/
    int[] PoctyLidi2 = poctyLidi;
 
    //Čekání na stisk klávesy -> ukončení programu
    Console.ReadKey();
}

Kód 1: Příklad kopie reference, kterou používá první instance jednorozměrného pole 

Podstata předchozího kódu (viz Kód 1) je zachycena v následujícím obrázku – viz Obrázek 1. Pokud tedy měníme některý prvek v poli poctyLidi2, mění se zároveň prvek v poli poctyLidi.

Přiřazení reference na stejný blok paměti na haldě

Obrázek 1: Přiřazení reference na stejný blok paměti na haldě


Jak tedy vytvořit kopii pole, tj. vytvoření instance s kopií obsahů jednotlivých prvků, které jsou uloženy na haldě?


Ilustrativní příklad PoleLidiKopie
Program PoleLidiKopie
  • Popis: Kopie obsahů všech celočíselných prvků jednorozměrného pole pomocí cyklu s krokem
  • Zadání: Vytvořte instanci jednorozměrného celočíselného pole o 5 prvcích: 7, 5, 2, 4, 9. Instance se bude jmenovat poctyLidi. V metodě Main zkopírujte obsah všech celočíselných prvků pole poctyLidi a nazvěte jej kopie
  • Řešení: Bude postupně probráno v následujícím textu

Postup v kódu je následující: musíme vytvořit nové pole (tj. novou instanci) stejného datového typu, jako je kopírované pole. Toto pole (instance) musí mít stejnou délku jako kopírované pole – viz Kód 2. Dále musíme kopírovat obsah všech prvků kopírovaného pole do prvků nově vytvářeného pole. Pro určení velikosti pole, tak i  pro určení počtu iterací v cyklu, použijeme vlastnosti Length, která poskytne velikost kopírovaného pole.

static void Main(string[] args)
{
    //Vytvoření instance pole o 5 prvcích včetně inicializace
    int[] poctyLidi = { 7, 5, 2, 4, 9 };
 
    /*Vytvoření nového pole (instance) se stejnou délkou jakou má 
     * kopírované pole (instance)*/
    int[] kopie = new int[poctyLidi.Length];
    //Procházení všech prvků pole
    for (int i = 0; i < poctyLidi.Length; i++)
    {
        //Přiřazení obsahu prvku kopírovaného pole do nově vytvořeného pole
        kopie[i] = poctyLidi[i];
    }            
}

Kód 2: Kopie jednorozměrného pole

Podstata předchozího kódu (viz Kód 2) je zachycena v následujícím obrázku – viz Obrázek 2. Pokud tedy měníme některý prvek v poli kopie, již se nebude měnit prvek v poli poctyLidi.

Kopie pole

Obrázek 2: Vytvoření kopie pole


Ilustrativní příklad PoleLidiCopyTo
Program PoleLidiCopyTo
  • Popis: Kopie obsahů všech celočíselných prvků jednorozměrného pole pomocí metody CopyTo
  • Zadání: Vytvořte instanci jednorozměrného celočíselného pole o 5 prvcích: 7, 5, 2, 4, 9. Instance se bude jmenovat poctyLidi. V metodě Main zkopírujte obsah všech celočíselných prvků pole poctyLidí pomocí metody CopyTo a nazvěte jej kopie
  • Řešení: Bude postupně probráno v následujícím textu

 

Kopírování pole je dosti běžnou činností, proto třída System.Array nabízí některé užitečné metody pro práci s polem např. CopyTo – viz Kód 3. Tato metoda zkopíruje obsah pole do jiného pole vzhledem k zadanému počátečnímu indexu, odkud se mají prvky pole kopírovat.

static void Main(string[] args)
{
    //Vytvoření instance pole o 5 prvcích včetně inicializace
    int[] poctyLidi = { 7, 5, 2, 4, 9 };
 
    //Vytvoření nového pole se stejnou délkou jako kopírované pole
    int[] kopie = new int[poctyLidi.Length];
 
    //Kopírování všech prvků od indexu 0
    poctyLidi.CopyTo(kopie, 0);
}

Kód 3: Kopie jednorozměrného pole poctyLidi pomocí metody CopyTo


Ilustrativní příklad PoleLidiCopy
Program PoleLidiCopy
  • Popis: Kopie obsahů všech celočíselných prvků jednorozměrného pole pomocí metody Copy
  • Zadání: Vytvořte instanci jednorozměrného celočíselného pole o 5 prvcích: 7, 5, 2, 4, 9. Instance se bude jmenovat poctyLidi. V metodě Main zkopírujte obsah všech celočíselných prvků pole poctyLidí pomocí metody Array.Copy a nazvěte jej kopie
  • Řešení: Bude postupně probráno v následujícím textu

Dalším způsobem kopírování pole je použít statickou metodu Copy třídy System.Array. Stejně jako u metody CopyTo musíme před voláním metody Copy vytvořit instanci pole, kam budeme kopírovat obsah kopírovaného pole – viz Kód 4. Pokud nezadáme platnou hodnotu délky pole např. zápornou hodnotu, metoda vyvolá výjimka typu ArgumentOutOfRangeException. V opačném případě specifikovaní větší délky, než je skutečná délka zdrojového pole, metoda vyvolá výjimku ArgumentException.

static void Main(string[] args)
{
    //Vytvoření instance pole o 5 prvcích včetně inicializace
    int[] poctyLidi = { 7, 5, 2, 4, 9 };
 
    //Vytvoření nového pole se stejnou délkou jako kopírované pole
    int[] kopie = new int[poctyLidi.Length];
 
    //Kopírování všech prvků - v závorce: zdrojové pole, cílové pole, délka pole
    Array.Copy(poctyLidi, kopie, kopie.Length);
}

Kód 4: Kopie jednorozměrného pole poctyLidi  pomocí metody Array.Copy


Ilustrativní příklad PoleLidiClone
Program PoleLidiClone
  • Popis: Kopie obsahů všech celočíselných prvků jednorozměrného pole pomocí metody Clone
  • Zadání: Vytvořte instanci jednorozměrného celočíselného pole o 5 prvcích: 7, 5, 2, 4, 9. Instance se bude jmenovat poctyLidi. V metodě Main klonujte obsah všech celočíselných prvků pole poctyLidí pomocí metody Clone a nazvěte jej kopie
  • Řešení: Bude postupně probráno v následujícím textu

Další alternativou kopírování pole je metoda Clone třídy System.Array. Tato metoda vytvoří a zároveň zkopíruje obsah pole – viz Kód 5. Tato metoda vrací jako výsledek datový typ object. Proto objekt musí být přetypován na datový typ prvků pole, abychom jej mohli přiřadit kopii pole.

static void Main(string[] args)
{
    //Vytvoření instance pole o 5 prvcích včetně inicializace
    int[] poctyLidi = { 7, 5, 2, 4, 9 };
 
    //Vytvoření klonovaného pole jako typ object -> přetypování
    int[] kopie = (int[])poctyLidi.Clone();
}

Kód 5: Klonování jednorozměrného pole poctyLidi  pomocí metody Clone


Metody Clone, CopyTo a Copy vytvářejí mělkou kopii (anglicky „Shalow Copy ") pole. Pokud prvky ve zkopírovaném poli obsahují odkazy, metoda Clone zkopíruje odkazy namísto samotných objektů. Po zkopírování se obě pole odkazují na stejné objekty. Pokud potřebujeme vytvořit hlubokou kopii (anglicky "Deep Copy") takového pole, musíme použít příslušný kód ve smyčce for - Obrázek 2. [6]

10. Vícerozměrná pole

Dvourozměrné pole

Jednorozměrná pole jsme vnímali jako seznam jednotlivých prvků. Pole ale může mít více než jednu dimenzi. Zaměřme se nyní na deklaraci např. dvourozměrného pole označované jako matice (dimenze takového pole je tedy rovna 2). Do prvků matice lze ukládat různé datové typy. Pokud bychom chtěli např. do matice ukládat celá čísla, deklarace takové matice by vypadala následovně - viz Kód 1. 

//Deklarace dvourozměrného pole
int[,] matice;

Kód 1: Příklad deklarace dvourozměrného pole

Dvourozměrné pole si lze si představit jako tabulku o řádcích a sloupcích, nebo také jako více jednorozměrných polí uspořádaných za sebou. Pro přístup k jednotlivým prvkům matice je zapotřebí dvou celočíselných indexů - viz Obrázek 1.

  • První celočíselný index pro řádky např.  i  (index řádky je číslován od 0. Počet řádků matice můžeme označit např.  m )
  • Druhý celočíselný index pro sloupce např.   j   (index sloupce je číslován od 0. Počet sloupců matice můžeme označit např.  n )

Deklarace dvourozměrného pole

Obrázek 1: Podstata dvourozměrného pole - matice (rozměr m × n)

Pro tvorbu instance dvourozměrného pole o velikosti  m \times n   bychom použili následující kód – viz Kód 2.

//Vytvoření instance dvourozměrného pole o specifikované velikosti (rozměr m x n)
int[,] matice = new int[m, n];

Kód 2: Deklarace dvourozměrného pole matice (rozměr m × n)

Abychom přistoupili k hodnotě uložené v prvku dvourozměrného pole, využijeme indexů uzavřených v hranatých závorkách, které odrážejí polohu prvku pole, např.  matice[i,j] . Následující obrázek vyjadřuje podstatu indexování jednotlivých prvků dvourozměrného pole o rozměrech  m \times n  - viz Obrázek 2.

Indexování prvků dvourozměrného pole

Obrázek 2: Indexování prvků dvourozměrného pole matice (rozměr m × n)

Pokud je matice symetrická  m=n , označujeme úhlopříčnou spojnici protilehlých míst (prvního prvku a posledního prvku) jako hlavní diagonálu - viz Obrázek 3. Pro prvky na hlavní diagonále platí, že jejich index řádku  i je roven indexu sloupce  j , tj.  i=j . 

Indexování prvků na hlavní diagonále ve dvourozměrném poli

Obrázek 3: Indexování prvků na hlavní diagonále ve dvourozměrném poli

Pokud je matice symetrická  m=n , označujeme protilehlou úhlopříčnou spojnici protilehlých míst (posledního prvku prvního řádku a prvního prvku posledního řádku) jako vedlejší diagonálu - viz Obrázek 4. Pro prvky na vedlejší diagonále platí, že jejich index řádku  i je roven indexu sloupce tehdy, když  j=(n-i-1).  Pro případ matice o rozměru např.  4 \times 4  jsou prvky umístěné na vedlejší diagonále označeny modře. 

Indexování prvků na vedlejší diagonále ve dvourozměrném poli (rozměr 4 x 4)

Obrázek 4: Indexování prvků na vedlejší diagonále ve dvourozměrném poli ( 4 \times 4 )


Ilustrativní příklad MaticeVedlejsiDiagonala

Program MaticeVedlejsiDiagonala
  • Popis: Deklarace dvourozměrného pole, velikost pole, instance pole, vedlejší diagonála
  • Zadání: Deklarujte symetrické dvourozměrné pole s názvem matice. Toto pole bude obsahovat celočíselné hodnoty. Pomocí statické metody VytvorMatici, kde matice je výstupním parametrem, automaticky naplňte matici příslušnými hodnotami, které budou vzrůstat po sloupcích v každém řádku, tzn. první prvek první řádky, tj. vlevo nahoře, obsahuje hodnotu 1, další prvek v sousedním sloupci vpravo bude obsahovat 2, atd. Přiřazení hodnoty aktuálnímu prvku proveďte pomocí proměnné hodnotaPrvku. Plnění proveďte pomocí dvou cyklů s krokem - cyklus pro procházení řádek a další vnořený cyklus pro procházení sloupců. V metodě VytvorMatici také načtěte rozměry matice - proměnná m bude obsahovat počet řádků matice, proměnná n bude obsahovat počet sloupců matice. Pro výpis hodnot prvků na vedlejší diagonále použijte statickou metodu VedlejsiDiagonala do níž matici předejte. U výpisu každého prvku na vedlejší diagonále uveďte v hranaté závorce index řádku a index sloupce oddělené čárkou. Obě metody jsou volány v hlavní metodě Main
  • Řešení: MaticeVedlejsiDiagonala_Main


Nejprve si ve zdrojovém kódu metody VytvorMatici s výstupním parametrem představující vytvořenou výstupní matici (klíčové slovo out deklaruje výstupní parametr, datový typ int deklaruje, že se jedná o celočíselnou matici a čárka mezi hranatými závorkami deklaruje, že se jedná o dvourozměrné pole s názvem matice). V metodě deklarujeme proměnnou, jejíž hodnotu budeme zvedat po přiřazení této hodnoty každému prvku matice - viz Kód 3.  

//Deklarace metody, kde dvourozměrné pole je deklarováno jako výstupní parametr metody
public static void VytvorMatici(out int[ , ] matice)
{
    <span style="color:green;">// Deklarace proměnné: 'hodnota' - hodnota v prvku</span>
    <span style="color:blue;">int</span> <span style="color:#1f377f;">hodnotaPrvku</span> = 1;
}

Kód 3: Deklarace metody VytvorMatici s výstupním parametrem matice

V těle metody vybídneme uživatele pro zadání celkového počtu řádků matice - viz Kód 4. Tento zadaný rozměr matice si načteme do proměnné m. 

//Výpis textu pro zadání počtu řádků matice
Console.Write("Zadejte počet řádků matice: ");
/* Deklarace proměnné 'm' - počet řádků matice
 * + konverze zadaného textu na číslo */
int m = int.Parse(Console.ReadLine());

Kód 4: Vypsání textu pro zadání počtu řádků matice včetně načtení a konverze zadaného textu na celé číslo

Abychom splnili zadání symetrické matice, tj. m = n, vytvoříme v dalším kroku cyklus, který vybídne uživatele k zadání celkového počtu sloupců matice. Pokud uživatel zadá hodnotu počtu sloupců (uložené do proměnné n) různou od hodnoty uložené v proměnné m, je provedena znovu smyčku cyklu pro zadání hodnoty n - viz Kód 5. Proměnnou n jsme deklarovali již před cyklem, abychom v cyklu pouze zajistili zadání validní hodnoty této proměnné a nevytvářeli znovu a znovu novou proměnnou.

// Deklarace proměnné: 'n' - celkový počet sloupců matice
int n;
do
{            
    <span style="color:green;">//Výpis textu pro zadání počtu sloupců matice</span>
    <span style="color:#2b91af;">Console</span>.<span style="color:#74531f;">Write</span>(<span style="color:#a31515;">"Zadejte počet sloupců matice: "</span>);
    <span style="color:green;">/* Deklarace proměnné 'n' - počet sloupců matice
       * + konverze zadaného textu na číslo */</span>
     <span style="color:#1f377f;">n</span> = <span style="color:blue;">int</span>.<span style="color:#74531f;">Parse</span>(<span style="color:#2b91af;">Console</span>.<span style="color:#74531f;">ReadLine</span>());
}
//Prováděj cyklus pokud n je různé od m
while (n != m);

Kód 5: Načtení validní hodnoty počtu sloupců matice

Pro vytvoření instance dvourozměrného pole o rozměru m × n využijeme následující kód - viz Kód 6. K vytvoření instance pole se užívá klíčové slovo new. Tento operátor vrátí odkaz na nově vytvořené pole. Za operátorem new se uvádí datový typ prvků. Za datovým typem se uvádí v hranatých závorkách počet prvků dvourozměrného pole v každé ose.

//Vytvoření instance dvourozměrného pole o specifikované velikosti
matice = new int[m, n];

Kód 6: Vytvoření instance dvourozměrného pole o specifikované velikosti

Pokud by celkový počet řádků matice, uložený v proměnné m, byl roven 4 a celkový počet sloupců v proměnné n byl také roven hodnotě 4, měla by výsledná matice vypadat následovně - viz Obrázek 5. 

Naplnění dvourozměrného celočíselného pole (rozměr 4 x 4)

Obrázek 5: Naplnění dvourozměrného celočíselného pole matice (rozměr 4 x 4)

Pro přiřazení hodnoty aktuálně procházeného prvku pomocí celočíselné proměnné hodnotaPrvku (v našem případě prvky budou nabývat hodnot 1 ÷ 16)  budeme používat dva cykly s krokem (víme, kolik iterací má proběhnout). Proměnnou hodnotaPrvku jsme inicializovali hodnotou 1 již při její deklaraci (toto je hodnota prvku v prvním řádku a prvním sloupci, tj. matice[0, 0]). První cyklus obsahuje řídící proměnnou i, která nám určuje pozici řádku právě procházeného prvku. Ve vnitřním (vnořeném)  cyklu s řídící proměnnou j, budeme procházet sloupce matice. Index j nám tedy určuje aktuální sloupec procházeného prvku - viz Kód 7. 

//Cyklus procházející jednotlivé řádky matice
for (int i = 0; i < m; i++)
{
    <span style="color:green;">//Cyklus procházející jednotlivé sloupce matice</span>
    <span style="color:#8f08c4;">for</span> (<span style="color:blue;">int</span> <span style="color:#1f377f;">j</span> = 0; <span style="color:#1f377f;">j</span> < <span style="color:#1f377f;">n</span>; <span style="color:#1f377f;">j</span>++)
    {
        <span style="color:green;">//Přiřazení hodnoty prvku matice</span>
        <span style="color:#1f377f;">matice</span>[<span style="color:#1f377f;">i</span>, <span style="color:#1f377f;">j</span>] = <span style="color:#1f377f;">hodnotaPrvku</span>++;
    }
}

Kód 7: Přiřazení hodnot prvkům matice

Pro výpis prvků na vedlejší diagonále matice deklarujeme metodu bez návratu s názvem VedlejsiDiagonala. Tato metoda obsahuje formální vstupní parametr matice. Deklarace tohoto parametru je stejná jako v předchozí metodě VytvorMatici (samozřejmě bez klíčového slova out - matici nevytváříme, potřebujeme pouze projít její prvky a vypsat je v konzole). V této metodě využijeme znovu vnořený cyklus s krokem (namísto cyklu foreach - máme totiž uživatele informovat o aktuálním indexu řádku a sloupce právě vypisovaného prvku na vedlejší diagonále matice). Tyto indexy mají být uzavřeny do hranatých závorek.

//Deklarace metody vypisující obsah všech prvků na vedlejší diagonále dvourozměrného pole
public static void VedlejsiDiagonala(int[ , ] matice)
{
    <span style="color:green;">//Cyklus procházející jednotlivé řádky matice</span>
    <span style="color:#8f08c4;">for</span> (<span style="color:blue;">int</span> <span style="color:#1f377f;">i</span> = 0; <span style="color:#1f377f;">i</span> < <span style="color:#1f377f;">matice</span>.<span style="color:#74531f;">GetLength</span>(0); <span style="color:#1f377f;">i</span>++)
    {
        <span style="color:green;">//Cyklus procházející jednotlivé sloupce matice</span>
        <span style="color:#8f08c4;">for</span> (<span style="color:blue;">int</span> <span style="color:#1f377f;">j</span> = 0; <span style="color:#1f377f;">j</span> < <span style="color:#1f377f;">matice</span>.<span style="color:#74531f;">GetLength</span>(1); <span style="color:#1f377f;">j</span>++)
        {
            <span style="color:green;">//Pokud se prvek nachází ve vedlejší diagonále</span>
            <span style="color:#8f08c4;">if</span> (<span style="color:#1f377f;">j</span> == <span style="color:#1f377f;">matice</span>.<span style="color:#74531f;">GetLength</span>(1) - <span style="color:#1f377f;">i</span> - 1)                    
                <span style="color:green;">//Výpis textu s obsahem prvku včetně pozice prvku</span>
                <span style="color:#2b91af;">Console</span>.<span style="color:#74531f;">WriteLine</span>(<span style="color:#a31515;">"Hodnota prvku matice[{0}, {1}]: {2}", i, j, matice[i, j]);
        }
    }
}

Kód 8: Deklarace metody VedlejsiDiagonala

V hlavní metodě Main jsme nejprve vytvořili dvourozměrné pole pomocí metody VytvorMatici s výstupním parametrem matice. Tato metoda vytváří instanci dvourozměrného pole a zároveň toto pole naplní hodnotami pořadových čísel prvků v matici (za předpokladu, že procházíme jednotlivé řádky matice zleva doprava). Po vytvoření matice stačilo již vypsat prvky na vedlejší diagonále matice pomocí metody bez návratu s názvem VedlejsiDiagonala - viz Kód 9.

static void Main(string[] args)
{
    <span style="color:green;">//Zavolání metody s výstupním parametrem matice</span>
    <span style="color:#74531f;">VytvorMatici</span>(<span style="color:blue;">out</span> <span style="color:blue;">int</span>[,] <span style="color:#1f377f;">matice</span>);
 
    <span style="color:green;">//Zavolání metody pro vypsání prvků na vedlejší diagonále matice</span>
    <span style="color:#74531f;">VedlejsiDiagonala</span>(<span style="color:#1f377f;">matice</span>);
 
    <span style="color:green;">//Čekání na stisk klávesy -> ukončení programu</span>
    <span style="color:#2b91af;">Console</span>.<span style="color:#74531f;">ReadKey</span>();
}

Kód 9: Deklarace hlavní metody Main

Na výpisu v konzoli vidíme výstup našeho programu. Na druhém řádku výpisu je zaznamenán pokus o zadání jiného počtu sloupců, než byla hodnota celkového počtu řádků matice. Zde zafungoval cyklus, který uživateli nedovolí zadat jinou celočíselnou hodnotu, než je počet řádků matice. Při správném zadání celkového počtu sloupců tj. rozměru matice 4 x 4 jsou vypsány hodnoty všech prvků na vedlejší diagonále včetně indexu řádku a sloupce těchto prvků - viz Výstup programu -  MaticeVedlejsiDiagonala_Main.

Zadejte počet řádků matice: 4
Zadejte počet sloupců matice: 5
Zadejte počet sloupců matice: 4
Hodnota prvku matice[0, 3]: 4
Hodnota prvku matice[1, 2]: 7
Hodnota prvku matice[2, 1]: 10
Hodnota prvku matice[3, 0]: 13

Výstup programu - MaticeVedlejsiDiagonala_Main: Výpis prvků dvourozměrné pole - matice (rozměr 4 x 4) 


Trojrozměrná a vícerozměrná pole

Pokud bychom chtěli vytvořit tzv. kostku (anglicky "Cube"), tedy trojrozměrné symetrické pole, stačí pouze v deklaraci pole přidat do hranaté závorky další čárku. Tím definujeme další třetí rozměr pole. Pomocí následujícího kódu vytvoříme instanci trojrozměrné pole o rozměru (5 × 5 × 5) - viz Kód 10.

//Deklarace trojrozměrného pole
int[,,] kostka = new int[5, 5, 5];

Kód 10: Příklad deklarace trojrozměrného pole a vytvoření instance tohoto typu pole (kostky)

Lze si tedy odvodit, že pro přístup k jednotlivým prvkům tohoto pole je zapotřebí 3 indexů. Např. Pokud potřebujeme přiřadit hodnotu 1 prvnímu prvku levého horního rohu kostky budeme postupovat následujícím způsobem - viz Kód 11.

//Přiřazení hodnoty prvku levého horního rohu kostky
kostka[0, 0, 0] = 1;

Kód 11: Příklad přiřazení hodnoty prvku levého horního rohu kostky

Stejným způsobem bychom deklarovali další vícerozměrná pole. Počet dimenzí, které můžete u pole zadat, není nijak omezen, ale je také důležité zdůraznit opatrnost při vytváření polí s větším dimenzí než 3. Taková pole spotřebují mnoho paměti např. kostka o rozměrech 5 × 5 × 5 bude obsahovat 125 prvků. Pokud budeme vytvářet čtyřdimenzionální pole 5 × 5 × 5 × 5, tak toto pole bude obsahovat již 625 prvků. Proto buďte opatrní a zkuste využívat zpracování výjimky typu OutOfMemoryException.

11. Vícenásobná pole

V C# jsou vícedimenzionální pole označována jako pravoúhlá pole (anglicky "Rectangular Array"), kde každá dimenze má pravidelný tvar. Často však nepotřebujeme vyplnit všechny prvky takových polí a tím pádem jen zbytečně plýtváme pamětí na prázdné prvky. Proto je vhodné využít tzv. vícenásobné pole (anglicky "Jagged Array"). Vícenásobné pole je takové pole, jehož prvky obsahují další pole - někdy také označované "pole polí", nebo "zubatá matice". Prvky vícenásobného pole mohou mít různé velikosti. 

V následujícím zdrojovém kódu vidíme deklaraci vícenásobného pole včetně vytvoření instance vicenasobnePole - viz Kód 1. 

//Deklarace tří řádků vícenásobného pole (sloupce jsou prázdné)
int[][] vicenasobnePole = new int[3][];

Kód 1: Deklarace vícenásobného pole vicenasobnePole

Vícenásobné pole lze vnímat jako pole, které bude obsahovat tři prvky do kterých postupně umístíme další jednorozměrná celočíselná pole. Proto nejprve vytvoříme další tři instance jednorozměrných celočíselných polí o různé délce pojmenované pole0, pole1, pole2 - viz Kód 2.

//Deklarace jednorozměrných polí s různou délkou
int[] pole0 = new int[5];
int[] pole1 = new int[3];
int[] pole2 = new int[4];

Kód 2: Deklarace jednorozměrných polí

Podstata předchozích kódů je zobrazena na následujícím obrázku - viz Obrázek 1.

Deklarace vícenásobného pole a tří jednorozměrných polí

Obrázek 1: Deklarace vícenásobného pole a tří jednorozměrných polí 

Po vytvoření jednorozměrných polí provedeme jejich přiřazení (tzn. vytvoření odkazů) prvkům vícenásobného pole - viz Kód 3.

//Přiřazení jednotlivých polí řádkům vícenásobného pole
vicenasobnePole[0] = pole0;
vicenasobnePole[1] = pole1;
vicenasobnePole[2] = pole2;

Kód 3: Přiřazení polí do jednotlivých řádků (prvků) vícenásobného pole

Celá podstata přiřazení jednotlivým prvkům vícenásobného pole je zobrazena na následujícím obrázku - viz Obrázek 2.


Obrázek 2: Přiřazení jednorozměrných celočíselných polí prvkům vícenásobného pole

Uvědomme si, že přiřazení jednorozměrných polí o různé délce prvkům vícenásobného pole je pomocí referencí a nikoliv pomocí kopírování dat do těchto prvků. Pokud tedy změníme např. třetí prvek jednorozměrného pole pole0 (tedy pole0[2]), měníme tím také prvek vicenasobnePole[0] ve vícenásobném poli obsahující toto jednorozměrné pole, (tedy  vicenasobnePole[0] [2]). Následující zápis ve zdrojovém kódu na obou řádcích provádí přiřazení hodnoty třetího prvku pole0 - viz Kód 4.

//Přiřazení hodnoty třetímu prvku jednorozměrného 'pole0'
pole0[2] = 38;
/* Přiřazení hodnoty třetímu prvku jednorozměrného 'pole0' uloženého 
 * v prvním prvku vícenásobného pole */
vicenasobnePole[0][2] = 38;

Kód 4: Příkazy se stejnou podstatou - přiřazení hodnoty třetímu prvku jednorozměrného pole0

12. Stručné shrnutí


Stručné shrnutí kapitol
Pro ... ... proveďte následující
Deklarace proměnné typu pole Uveďte datový typ prvků v poli, za ním napište hranaté závorky, název proměnné a středník, např. pro jednorozměrné pole obsahující teploty jednotlivých dnů:
double[] teploty;
Vytvoření instance pole Za operátor přiřazení uveďte klíčové slovo new, název datového typu uchovávaných prvků a za něj velikost pole v hranatých závorkách, např.:
double[] teploty = new double[7];
Inicializaci prvků pole určitými hodnotami Uveďte vkládané hodnoty do složených závorek, kde jsou prvky odděleny čárkami a velikost pole je odvozena kompilátorem, např.:
double[] teploty = { 12.6, 12.5, 13.8, 11.6, 12.8, 13.5, 11.9};
Zjištění počtu prvků v poli Použijte vlastnost Length, např.:
double[] teploty = ... ;
...
int pocetPrvku = teploty.Length;
Přístup k prvku pole Uveďte název proměnné typu pole, za něj uveďte v hranatých závorkách index pozice prvku (indexy začínají 0):
double teplotaPondeli = teploty[0];
 Procházení prvků pole  Použijte příkaz for pro procházení prvků na základě indexu, např.:
for (int i = 0; i < teploty.Length; i++)
{
    Console.WriteLine(teploty[i]);
}
nebo použijte cyklus foreach:
foreach (double teplota in teploty)
{
    Console.WriteLine(teplota);
}