Aritmetické operátory (referenční dokumentace jazyka C#)
Následující operátory provádějí aritmetické operace s operandy číselných typů:
- Unární
++
operátory (inkrementace),--
(dekrement),+
(plus) a-
(minus) - Binární
*
operátory (násobení),/
(dělení),%
(zbytek),+
(sčítání) a-
(odčítání)
Tyto operátory jsou podporovány všemi celočíselnými a číselnými typy s plovoucí desetinou čárkou .
V případě integrálních typů jsou tyto operátory (kromě ++
operátorů --
) definovány pro operátory int
, uint
, long
a ulong
typy. Pokud jsou operandy jiného celočíselného typu (sbyte
, byte
, short
, ushort
nebo char
), jejich hodnoty se převedou na int
typ, což je také typ výsledku operace. Pokud jsou operandy různých integrálních typů nebo typů s plovoucí desetinou čárkou, jejich hodnoty se převedou na nejbližší typ obsahující, pokud takový typ existuje. Další informace najdete v části Číselné povýšení specifikace jazyka C#. Operátory ++
a operátory jsou definovány pro všechny celočíselné a číselné typy s plovoucí desetinou čárkou a typ znaku.--
Typ výsledku výrazu složeného přiřazení je typ levého operandu.
Operátor přírůstku ++
Unární operátor ++
přírůstku zvýší svůj operand o 1. Operand musí být proměnná, přístup k vlastnosti nebo přístup indexeru.
Operátor přírůstku je podporován ve dvou formách: operátor x++
přírůstku přípony a operátor přírůstku předpony, ++x
.
Příponový operátor inkrementace
Výsledek x++
je hodnota x
před operací, jak ukazuje následující příklad:
int i = 3;
Console.WriteLine(i); // output: 3
Console.WriteLine(i++); // output: 3
Console.WriteLine(i); // output: 4
Operátor přírůstku předpony
Výsledek ++x
je hodnota x
za operací, jak ukazuje následující příklad:
double a = 1.5;
Console.WriteLine(a); // output: 1.5
Console.WriteLine(++a); // output: 2.5
Console.WriteLine(a); // output: 2.5
Operátor dekrementace --
Unární --
dekrement operátor dekrementuje svůj operand o 1. Operand musí být proměnná, přístup k vlastnosti nebo přístup indexeru.
Operátor dekrementu je podporován ve dvou formách: operátor x--
dekrementace přípony a operátor dekrementace předpony . --x
Příponový operátor dekrementace
Výsledek x--
je hodnota x
před operací, jak ukazuje následující příklad:
int i = 3;
Console.WriteLine(i); // output: 3
Console.WriteLine(i--); // output: 3
Console.WriteLine(i); // output: 2
Operátor dekrementace předpony
Výsledek --x
je hodnota x
za operací, jak ukazuje následující příklad:
double a = 1.5;
Console.WriteLine(a); // output: 1.5
Console.WriteLine(--a); // output: 0.5
Console.WriteLine(a); // output: 0.5
Unární operátory plus a minus
Unární +
operátor vrátí hodnotu svého operandu. Unární -
operátor vypočítá číselnou negaci svého operandu.
Console.WriteLine(+4); // output: 4
Console.WriteLine(-4); // output: -4
Console.WriteLine(-(-4)); // output: 4
uint a = 5;
var b = -a;
Console.WriteLine(b); // output: -5
Console.WriteLine(b.GetType()); // output: System.Int64
Console.WriteLine(-double.NaN); // output: NaN
Typ ulong nepodporuje unární -
operátor.
Operátor násobení *
Operátor *
násobení vypočítá součin svých operandů:
Console.WriteLine(5 * 2); // output: 10
Console.WriteLine(0.5 * 2.5); // output: 1.25
Console.WriteLine(0.1m * 23.4m); // output: 2.34
Unární *
operátor je operátor nepřímého ukazatele.
Operátor dělení /
Operátor /
dělení rozdělí operand na levé straně jeho operandem zprava.
Celočíselné dělení
U operandů celočíselného typu je výsledkem /
operátoru celočíselného typu a rovná se podílu dvou operandů zaokrouhlených na nulu:
Console.WriteLine(13 / 5); // output: 2
Console.WriteLine(-13 / 5); // output: -2
Console.WriteLine(13 / -5); // output: -2
Console.WriteLine(-13 / -5); // output: 2
Chcete-li získat podíl dvou operandů jako číslo s plovoucí desetinou čárkou, použijte float
hodnotu , double
nebo decimal
zadejte:
Console.WriteLine(13 / 5.0); // output: 2.6
int a = 13;
int b = 5;
Console.WriteLine((double)a / b); // output: 2.6
Dělení s plovoucí desetinou čárkou
float
Pro operátor , double
a decimal
typy je výsledek /
operátoru podíl dvou operandů:
Console.WriteLine(16.8f / 4.1f); // output: 4.097561
Console.WriteLine(16.8d / 4.1d); // output: 4.09756097560976
Console.WriteLine(16.8m / 4.1m); // output: 4.0975609756097560975609756098
Pokud je jeden z operandů decimal
, jiný operand nemůže být ani float
double
, protože ani není float
double
implicitně konvertibilní na decimal
. Musíte explicitně převést float
nebo double
operand na decimal
typ. Další informace o převodech mezi číselnými typy naleznete v tématu Předdefinované číselné převody.
Operátor zbytku %
Operátor zbytku %
vypočítá zbytek po vydělení levého operandu jeho operandem zprava.
Zbytek celého čísla
Pro operandy celočíselného typu je výsledkem a % b
hodnoty, kterou a - (a / b) * b
vytváří . Znaménko nenulového zbytku je stejné jako znaménko levého operandu, jak ukazuje následující příklad:
Console.WriteLine(5 % 4); // output: 1
Console.WriteLine(5 % -4); // output: 1
Console.WriteLine(-5 % 4); // output: -1
Console.WriteLine(-5 % -4); // output: -1
Použijte metodu Math.DivRem k výpočtu celočíselného dělení i výsledků zbytku.
Zbytek s plovoucí desetinou čárkou
float
U operandů a double
operandů je výsledek x % y
konečné x
y
hodnoty, která je taková, z
že
- Znaménko
z
, pokud není nula, je stejné jako znaménkox
. - Absolutní hodnota je hodnota
z
vytvořená tam, kden
|x| - n * |y|
je největší možné celé číslo, které je menší než nebo rovno|x| / |y|
a|x|
jsou|y|
absolutními hodnotamix
ay
v uvedeném pořadí.
Poznámka:
Tato metoda výpočtu zbytku je podobná té, která se používá pro celočíselné operandy, ale liší se od specifikace IEEE 754. Pokud potřebujete zbývající operaci, která splňuje specifikaci IEEE 754, použijte metodu Math.IEEERemainder .
Informace o chování operátoru %
s nekonficiálními operandy naleznete v části Operátor zbytku specifikace jazyka C#.
decimal
U operandů je operátor %
zbytku ekvivalentní operátoru zbytku System.Decimal typu.
Následující příklad ukazuje chování operátoru zbytku s operandy s plovoucí desetinou čárkou:
Console.WriteLine(-5.2f % 2.0f); // output: -1.2
Console.WriteLine(5.9 % 3.1); // output: 2.8
Console.WriteLine(5.9m % 3.1m); // output: 2.8
Operátor sčítání +
Operátor sčítání +
vypočítá součet svých operandů:
Console.WriteLine(5 + 4); // output: 9
Console.WriteLine(5 + 4.3); // output: 9.3
Console.WriteLine(5.1m + 4.2m); // output: 9.3
Operátor můžete použít +
také pro zřetězení řetězců a kombinaci delegátů. Další informace najdete v +
článku a +=
operátory .
Operátor odčítání –
Operátor -
odčítání odečte svůj operand z levého operandu:
Console.WriteLine(47 - 3); // output: 44
Console.WriteLine(5 - 4.3); // output: 0.7
Console.WriteLine(7.5m - 2.3m); // output: 5.2
Operátor můžete také použít k odebrání delegáta -
. Další informace najdete v -
článku a -=
operátory .
Složené přiřazení
U binárního operátoru op
je složený výraz přiřazení formuláře.
x op= y
je ekvivalentem
x = x op y
s tím rozdílem, že x
se vyhodnotí pouze jednou.
Následující příklad ukazuje použití složeného přiřazení s aritmetických operátorů:
int a = 5;
a += 9;
Console.WriteLine(a); // output: 14
a -= 4;
Console.WriteLine(a); // output: 10
a *= 2;
Console.WriteLine(a); // output: 20
a /= 4;
Console.WriteLine(a); // output: 5
a %= 3;
Console.WriteLine(a); // output: 2
Z důvodu číselných povýšení nemusí být výsledek op
operace implicitně konvertibilní na typ T
x
. V takovém případě je-li op
předdefinovaný operátor a výsledek operace je explicitně konvertibilní na typ x
T
, složený výraz přiřazení formuláře x op= y
je ekvivalentní x = (T)(x op y)
, s výjimkou toho, že x
je vyhodnocen pouze jednou. Následující příklad ukazuje toto chování:
byte a = 200;
byte b = 100;
var c = a + b;
Console.WriteLine(c.GetType()); // output: System.Int32
Console.WriteLine(c); // output: 300
a += b;
Console.WriteLine(a); // output: 44
V předchozím příkladu je výsledkem 44
převodu hodnoty 300
na byte
typ.
Poznámka:
V kontextu kontroly přetečení vyvolá předchozí příklad chybu OverflowException. Další informace najdete v části aritmetické přetečení celého čísla.
Operátory a -=
operátory +=
také používáte k přihlášení k odběru a odhlášení odběru události. Další informace najdete v tématu Jak se přihlásit k odběru a odhlásit odběr událostí.
Priorita operátorů a asociativita
Následující seznam obsahuje aritmetické operátory počínaje nejvyšší prioritou až po nejnižší:
- Operátory přírůstku a dekrementace
x++
x--
přípony - Inkrementace a dekrementace
++x
--x
předpony a unární+
operátory a-
operátory - Multiplikativní
*
,/
a%
operátory - Sčítání
+
a-
operátory
Binární aritmetické operátory jsou asociativní zleva. To znamená, že operátory se stejnou úrovní priority se vyhodnocují zleva doprava.
Pomocí závorek ()
změňte pořadí vyhodnocení uloženého podle priority operátoru a asociativity.
Console.WriteLine(2 + 2 * 2); // output: 6
Console.WriteLine((2 + 2) * 2); // output: 8
Console.WriteLine(9 / 5 / 2); // output: 0
Console.WriteLine(9 / (5 / 2)); // output: 4
Úplný seznam operátorů jazyka C# seřazených podle úrovně priority najdete v části Priorita operátorů v článku operátory jazyka C#.
Aritmetické přetečení a dělení nulou
Pokud je výsledek aritmetické operace mimo rozsah možných konečných hodnot zahrnutého číselného typu, chování aritmetického operátoru závisí na typu jeho operandů.
Celočíselná aritmetická přetečení
Celočíselné dělení nulou vždy vyvolá DivideByZeroExceptionhodnotu .
Pokud dojde k aritmetickému přetečení celého čísla, řídí výsledný chování kontext kontroly přetečení, který lze zkontrolovat nebo zrušit zaškrtnutím tohoto políčka:
- Pokud v kontrolovaném kontextu dojde v konstantním výrazu k přetečení, dojde k chybě v době kompilace. V opačném případě je vyvolán při provedení operace za běhu OverflowException .
- V nezaškrtnutém kontextu se výsledek zkrátí tak, že zahodí všechny bity s vysokým pořadím, které se nevejdou do cílového typu.
Spolu se zaškrtnutými a nezaškrtnutými příkazy můžete pomocí checked
operátorů unchecked
řídit kontext kontroly přetečení, ve kterém se výraz vyhodnotí:
int a = int.MaxValue;
int b = 3;
Console.WriteLine(unchecked(a + b)); // output: -2147483646
try
{
int d = checked(a + b);
}
catch(OverflowException)
{
Console.WriteLine($"Overflow occurred when adding {a} to {b}.");
}
Ve výchozím nastavení se aritmetické operace vyskytují v nezaškrtnutém kontextu.
Aritmetické přetečení s plovoucí desetinou čárkou
Aritmetické operace s float
typy a double
nikdy nevyvolají výjimku. Výsledkem aritmetických operací s těmito typy může být jedna ze speciálních hodnot, které představují nekonečno a nikoli číslo:
double a = 1.0 / 0.0;
Console.WriteLine(a); // output: Infinity
Console.WriteLine(double.IsInfinity(a)); // output: True
Console.WriteLine(double.MaxValue + double.MaxValue); // output: Infinity
double b = 0.0 / 0.0;
Console.WriteLine(b); // output: NaN
Console.WriteLine(double.IsNaN(b)); // output: True
Pro operandy decimal
typu, aritmetické přetečení vždy vyvolá .OverflowException Dělení nulou vždy vyvolá chybu DivideByZeroException.
Chyby zaokrouhlení
Vzhledem k obecným omezením reprezentace skutečných čísel a aritmetických hodnot s plovoucí desetinou čárkou může ve výpočtech s typy s plovoucí desetinou čárkou dojít k chybám zaokrouhlení. To znamená, že vytvořený výsledek výrazu se může lišit od očekávaného matematického výsledku. Následující příklad ukazuje několik takových případů:
Console.WriteLine(.41f % .2f); // output: 0.00999999
double a = 0.1;
double b = 3 * a;
Console.WriteLine(b == 0.3); // output: False
Console.WriteLine(b - 0.3); // output: 5.55111512312578E-17
decimal c = 1 / 3.0m;
decimal d = 3 * c;
Console.WriteLine(d == 1.0m); // output: False
Console.WriteLine(d); // output: 0.9999999999999999999999999999
Další informace naleznete v poznámkách na stránkách odkazu System.Double, System.Single nebo System.Decimal .
Přetížení operátoru
Uživatelem definovaný typ může přetížit unární (++
, --
, +
a -
) a binární operátory (*
, /
, %
, +
, a ) aritmetické -
operátory. Pokud je binární operátor přetížen, odpovídající operátor složeného přiřazení je také implicitně přetížen. Uživatelem definovaný typ nemůže explicitně přetížit operátor složeného přiřazení.
Uživatelem definované kontrolované operátory
Počínaje jazykem C# 11 můžete při přetížení aritmetického operátoru definovat ověřenou verzi tohoto operátoru pomocí checked
klíčového slova. Následující příklad ukazuje, jak to udělat:
public record struct Point(int X, int Y)
{
public static Point operator checked +(Point left, Point right)
{
checked
{
return new Point(left.X + right.X, left.Y + right.Y);
}
}
public static Point operator +(Point left, Point right)
{
return new Point(left.X + right.X, left.Y + right.Y);
}
}
Při definování kontrolovaného operátoru musíte také definovat odpovídající operátor bez modifikátoru checked
. Kontrolovaný operátor se volá v kontrolovaném kontextu. Operátor bez modifikátoru checked
se volá v nezaškrtnutém kontextu. Pokud operátor zadáte pouze bez modifikátoru checked
, zavolá se v kontextu checked
i unchecked
v kontextu.
Při definování obou verzí operátoru se očekává, že se jejich chování liší pouze v případě, že výsledek operace je příliš velký, aby představoval v typu výsledku následujícím způsobem:
- Kontrolovaná operátor vyvolá výjimku OverflowException.
- Operátor bez modifikátoru
checked
vrátí instanci představující zkrácený výsledek.
Informace o rozdílu v chování předdefinovaných aritmetických operátorů najdete v části Aritmetické přetečení a dělení nulou .
Modifikátor můžete použít checked
pouze v případě, že přetížíte některý z následujících operátorů:
- Unární
++
,--
a-
operátory - Binární
*
,/
,+
, a-
operátory - Explicitní operátory převodu
Poznámka:
Kontext kontroly přetečení v těle kontrolního operátoru není ovlivněn přítomností modifikátoru checked
. Výchozí kontext je definován hodnotou CheckForOverflowUnderflow compiler option. checked
Pomocí příkazů můžete unchecked
explicitně určit kontext kontroly přetečení, jak ukazuje příklad na začátku této části.
specifikace jazyka C#
Další informace najdete v následujících částech specifikace jazyka C#:
- Operátory přírůstku a dekrementace přípony
- Operátory inkrementace a dekrementace předpon
- Unární operátor plus
- Unární operátor minus
- Operátor násobení
- Operátor dělení
- Operátor zbytku
- Operátor sčítání
- Operátor odčítání
- Složené přiřazení
- Zaškrtnuté a nezaškrtnuté operátory
- Číselné propagační akce