Operátory a přetypování – , as
typeof
a přetypování is
Tyto operátory a výrazy provádějí kontrolu typů nebo převod typů. Operátor is
zkontroluje, jestli je typ běhu výrazu kompatibilní s daným typem. Operátor as
explicitně převede výraz na daný typ, pokud je jeho typ za běhu kompatibilní s tímto typem. Přetypování výrazů provádí explicitní převod na cílový typ. Operátor typeof
získá System.Type instanci pro typ.
is – operátor
Operátor is
zkontroluje, jestli je typ běhu výsledku výrazu kompatibilní s daným typem. Operátor is
také testuje výsledek výrazu vůči vzoru.
Výraz s operátorem testování is
typu má následující formulář.
E is T
kde E
je výraz, který vrací hodnotu a T
je název typu nebo parametru typu. E
nemůže být anonymní metoda ani výraz lambda.
Operátor is
vrátí true
, když je výsledek výrazu nenulový a platí některé z následujících podmínek:
Typ běhu výsledku výrazu je
T
.Typ běhu výsledku výrazu je odvozen od typu
T
, implementuje rozhraníT
nebo jiný implicitní převod odkazu existuje z něj .T
Typ běhu výsledku výrazu je typ hodnoty null s podkladovým typem
T
a Nullable<T>.HasValue jetrue
.Převod boxingu nebo rozbalení existuje z typu běhu výsledku výrazu, který se má zadat
T
.
Operátor is
nebere v úvahu uživatelem definované převody.
Následující příklad ukazuje, že is
operátor vrátí true
, pokud typ běhu výsledku výrazu je odvozen z daného typu, to znamená, že existuje odkaz převodu mezi typy:
public class Base { }
public class Derived : Base { }
public static class IsOperatorExample
{
public static void Main()
{
object b = new Base();
Console.WriteLine(b is Base); // output: True
Console.WriteLine(b is Derived); // output: False
object d = new Derived();
Console.WriteLine(d is Base); // output: True
Console.WriteLine(d is Derived); // output: True
}
}
Další příklad ukazuje, že is
operátor bere v úvahu převody boxingu a rozbalování, ale nepovažuje za číselné převody:
int i = 27;
Console.WriteLine(i is System.IFormattable); // output: True
object iBoxed = i;
Console.WriteLine(iBoxed is int); // output: True
Console.WriteLine(iBoxed is long); // output: False
Informace o převodech jazyka C# naleznete v kapitole Převody specifikace jazyka C#.
Testování typů s odpovídajícími vzory
Operátor is
také testuje výsledek výrazu vůči vzoru. Následující příklad ukazuje, jak pomocí vzoru deklarace zkontrolovat typ běhu výrazu:
int i = 23;
object iBoxed = i;
int? jNullable = 7;
if (iBoxed is int a && jNullable is int b)
{
Console.WriteLine(a + b); // output 30
}
Informace o podporovanýchvzorch
Operátor as
Operátor as
explicitně převede výsledek výrazu na daný odkaz nebo typ hodnoty s možnou hodnotou null. Pokud převod není možný, as
vrátí null
operátor . Na rozdíl od výrazu as
přetypování operátor nikdy nevyvolá výjimku.
Výraz formuláře
E as T
kde E
je výraz, který vrací hodnotu a T
je názvem typu nebo parametru typu, vytvoří stejný výsledek jako
E is T ? (T)(E) : (T)null
s tím rozdílem, že E
se vyhodnotí pouze jednou.
Operátor as
bere v úvahu pouze převody odkazů, s možnou hodnotou null, boxing a unboxing. Operátor nelze použít as
k provedení uživatelem definovaného převodu. K tomu použijte výraz přetypování.
Následující příklad ukazuje použití operátoru as
:
IEnumerable<int> numbers = new List<int>(){10, 20, 30};
IList<int> indexable = numbers as IList<int>;
if (indexable != null)
{
Console.WriteLine(indexable[0] + indexable[indexable.Count - 1]); // output: 40
}
Poznámka:
Jak ukazuje předchozí příklad, je potřeba porovnat výsledek výrazu as
s null
cílem zkontrolovat, jestli převod proběhl úspěšně. Operátor is můžete použít k otestování, zda převod proběhne úspěšně, a pokud bude úspěšný, přiřaďte jeho výsledek k nové proměnné.
Přetypování výrazu
Výraz přetypování formuláře (T)E
provádí explicitní převod výsledku výrazu E
na typ T
. Pokud neexistuje žádný explicitní převod z typu E
na typ T
, dojde k chybě v době kompilace. V době běhu nemusí explicitní převod proběhnout úspěšně a výraz přetypování může vyvolat výjimku.
Následující příklad ukazuje explicitní číselné a referenční převody:
double x = 1234.7;
int a = (int)x;
Console.WriteLine(a); // output: 1234
int[] ints = [10, 20, 30];
IEnumerable<int> numbers = ints;
IList<int> list = (IList<int>)numbers;
Console.WriteLine(list.Count); // output: 3
Console.WriteLine(list[1]); // output: 20
Informace o podporovaných explicitních převodech najdete v části Explicitní převody specifikace jazyka C#. Informace o tom, jak definovat vlastní explicitní nebo implicitní převod typu, naleznete v tématu Uživatelem definované převodní operátory.
Další využití ()
Pomocí závorek můžete také volat metodu nebo vyvolat delegáta.
Dalším použitím závorek je úprava pořadí, ve kterém se mají vyhodnocovat operace ve výrazu. Další informace najdete v tématu Operátory jazyka C#.
typeof – operátor
Operátor typeof
získá System.Type instanci pro typ. Argument operátoru typeof
musí být název typu nebo parametru typu, jak ukazuje následující příklad:
void PrintType<T>() => Console.WriteLine(typeof(T));
Console.WriteLine(typeof(List<string>));
PrintType<int>();
PrintType<System.Int32>();
PrintType<Dictionary<int, char>>();
// Output:
// System.Collections.Generic.List`1[System.String]
// System.Int32
// System.Int32
// System.Collections.Generic.Dictionary`2[System.Int32,System.Char]
Argument nesmí být typem, který vyžaduje poznámky metadat. Mezi příklady patří následující typy:
dynamic
string?
(nebo jakýkoli typ odkazu s možnou hodnotou null)
Tyto typy nejsou přímo reprezentovány v metadatech. Typy zahrnují atributy, které popisují základní typ. V obou případech můžete použít základní typ. dynamic
Místo , můžete použít object
. string?
Místo , můžete použít string
.
Operátor můžete použít typeof
také s nevázanými obecnými typy. Název nevázaného obecného typu musí obsahovat odpovídající počet čárek, což je jedna menší než počet parametrů typu. Následující příklad ukazuje použití operátoru typeof
s nevázaným obecným typem:
Console.WriteLine(typeof(Dictionary<,>));
// Output:
// System.Collections.Generic.Dictionary`2[TKey,TValue]
Výraz nemůže být argumentem operátoru typeof
. Pokud chcete získat System.Type instanci pro typ běhu výsledku výrazu, použijte metodu Object.GetType .
Testování typů pomocí operátoru typeof
Pomocí operátoru typeof
zkontrolujte, jestli typ běhu výsledku výrazu přesně odpovídá danému typu. Následující příklad ukazuje rozdíl mezi kontrolou typů provedenou typeof
s operátorem a je operátor:
public class Animal { }
public class Giraffe : Animal { }
public static class TypeOfExample
{
public static void Main()
{
object b = new Giraffe();
Console.WriteLine(b is Animal); // output: True
Console.WriteLine(b.GetType() == typeof(Animal)); // output: False
Console.WriteLine(b is Giraffe); // output: True
Console.WriteLine(b.GetType() == typeof(Giraffe)); // output: True
}
}
Přetížení operátoru
Operátory a operátory is
nelze as
typeof
přetížit.
Uživatelem definovaný typ nemůže přetížit ()
operátor, ale může definovat vlastní převody typů, které lze provádět výrazem přetypování. Další informace naleznete v tématu Uživatelem definované operátory převodu.
specifikace jazyka C#
Další informace najdete v následujících částech specifikace jazyka C#: