Poznámka: články jsou již mnoho let staré, doba se posunula, mnoho věcí v nich doporučovaných je již dnes překonané - berte s rezervou!


Indexery - náhrada za přetížení operátoru [] (Zajímavé konstrukce jazyka C# II.)

Operátor [] (hranatice) se používá snad ve všech programovacích jazycích pro přímý přístup k položkám pole. Dovnitř hranatic se píše index prvku, na který chceme přistoupit.

Programátor občas ale zatouží po podobném principu u vlastních tříd. K tomu se dá v některých jazycích využít třeba mechanismus přetěžování operátorů, například v jazyce C++ to jde – tam jdou přetěžovat skoro všechny operátory, až na pár vyjímek. Pokud jste ale zkoušeli někdy skutečně robustně přetěžovat operátor [] u nějaké třídy, která se například kvůli realokacím může pohybovat po paměti (příkladem takové třídy může být např. pole proměnné velikosti), víte, jaký je to vopruz.

Problémem při přetěžování tohoto operátoru je totiž to, že ho programátor může v kódu použít na obou stranách rovnítka. Dokonce na obou stranách rovnítka najednou, na pravé ještě k tomu několikrát, když k tomu ještě připočtem to, že by mohl někdo používat hodnotu, vrácenou operátorem přiřazení v nějakém nadřazeném výrazu, je už oheň na střeše.

Asi kvůli častým chybám v přetěžování operátoru [] v jazyce C++ se rozhodli autoři C# tento operátor mezi přetížitelné nezahrnout (v C# je narozdíl od C++ množina přetížitelných operátorů velmi malá – ale aspoň něco, taková Java to nemá vůbec). Místo toho nabízí jiný způsob – takzvaný indexer. Indexer se deklaruje podobně jako se deklarují properties – tedy s modifikátory get a set. Příklad:

class MyClass { private int[] _a = new int[10]; public int this[int i] { get { return _a[i]; } set { _a[i] = value; } } }

Klíčové slovo this značí, že se jedná o indexer, za ním v hranaticích může být libovolný počet proměnných libovolných typů (ano, můžete indexovat pomocí více proměnných – tím můžete simulovat vícerozměrné pole – treba Sachovnice[X,Y] nebo provádět jiné kousky). Uvnitř těla indexeru pak je jeden nebo oba z modifikátorů přístupu get a set. (díky tomu, že jsou tu dva modifikátory přístupu, se vyřeší C++ problém s rozlišením toho, zda operátor stojí na levé nebo pravé straně rovnítka). Navíc u obou modifikátorů můžete kromě vlastního vrácení/nastavení hodnoty provádět jiné operace (kontroly na indexy a podobně).

Na závěr ještě jedna konstrukce, kterou překladač nezkousne.

class InvalidClass { private int[] _a = new int[10]; public int AsArray[int i] { get { return _a[i]; } set { _a[i] = value; } } } // //... // InvalidClass c = new InvalidClass; c.AsArray[i] = 1;

Tedy v hlavičce indexeru je vždy klíčové slovo this a řádek
public int AsArray
je špatně. Taková volnost v indexerech totiž není.

Indexerů může být v jedne třídě definováno několik – musí se ale lišit počtem nebo typem parametrů nebo návratovou hodnotou.

Používáním indexerů se váš kód stane přehlednějším a elegantnějším. Mnoho z tříd FCL indexery používá (typicky kolekce).

Ohodnoťte prosím užitečnost článku




17
 
13
 
15
 
17
 
2
 
 
Vložit komentář:
 

 



 

 

Nepoužívejte žádné html ani texy značky, odřádkování se zachová. Pokud uvádíte zdrojový kód, můžete ho vložit mezi značky
<syntax jazyk="PHP">...</syntax>,
bude potom zformátován. Jako atribut můžete uvést PHP, C#, HTML, CSS a mnoho dalších.


opiste cislo Opište číslo: