## 2.4 Operatoren Im vorigen Abschnitt haben wir uns eingehend mit den Daten auseinandergesetzt. Nun werden Sie lernen, wie diese Daten mit C# verarbeitet werden können. Bevor wir uns an die Details begeben, müssen wir uns zunächst mit der Terminologie befassen. An oberster Stelle steht der Begriff Ausdruck. Ein Ausdruck ist die kleinste ausführbare Einheit eines Programms und setzt mindestens einen Operator voraus. Im einfachsten Fall gilt schon die Anweisung
    value = 22;
als Ausdruck. Ein Ausdruck wird immer aus mindestens einem Operanden und einem Operator gebildet. Der Operator im Beispiel oben ist das Gleichheitszeichen, als Operand gelten sowohl die Konstante 22 als auch die Variable value. Operatoren verknüpfen Operanden miteinander und führen Berechnungen durch, ermitteln also als Ergebnis der Operation neue Werte. Nahezu alle Operatoren von C# benötigen zwei Operanden. Das Kernkonstrukt von Ausdrücken sind die Operatoren, die sich entsprechend ihrer Arbeitsweise in verschiedene Gruppen aufteilen lassen: arithmetische Operatoren Vergleichsoperatoren logische Operatoren bitweise Operatoren Zuweisungsoperatoren sonstige Operatoren ### 2.4.1 Arithmetische Operatoren C# kennt die üblichen Operatoren der vier Grundrechenarten Addition, Subtraktion, Division und Multiplikation. Darüber hinaus werden von dieser Gruppe noch weitere Operatoren beschrieben, die in ihrem Kontext eine besondere Bedeutung haben. Tabelle 2.6 gibt zunächst einen allgemeinen Überblick.

Tabelle 2.6 Arithmetische Operatoren

Operator | Beschreibung
+ | Hat zwei Funktionalitäten: Als Additionsoperator bildet er die Summe zweier Operanden (x + y). Als Vorzeichenoperator beschreibt er eine positive Zahl (+x), ist also ein einstelliger (unärer) Operator.
- | Hat ebenfalls zwei Funktionalitäten: Als Subtraktionsoperator eingesetzt, bildet er die Differenz zweier Operanden (x - y). Als unärer Vorzeichenoperator beschreibt er eine negative Zahl (-x).
* | Multiplikationsoperator; multipliziert zwei Operanden (x * y).
/ | Divisionsoperator; dividiert zwei Operanden (x / y) und behält den Nachkommateil der Division.
% | Restwertoperator; dividiert zwei Operanden und liefert als Ergebnis den Restwert der Operation (x % y).
++ | Erhöht den Inhalt des Operanden um 1. Das Ergebnis der Operation ++x ist der Wert des Operanden nach der Erhöhung (Präfixinkrementoperation). Das Ergebnis der Operation x++ ist der Wert des Operanden vor der Erhöhung (Postfixinkrementoperation).
-- | Verringert den Inhalt des Operanden um 1. Das Ergebnis der Operation --x ist der Wert des Operanden nach der Verringerung (Präfixdekrementoperation). Das Ergebnis der Operation x-- ist der Wert des Operanden vor der Verringerung (Postfixdekrementoperation).
Der Einsatz der Operatoren zur Formulierung mathematischer Ausdrücke ist trivial. Zwei Operanden werden miteinander verknüpft, und das Ergebnis der Operation wird der links vom Zuweisungsoperator stehenden Variablen zugewiesen.
    short srtVar1 = 30;
    short srtVar2 = 55;
    short srtResult = srtVar1 + srtVar2;
Eine besondere Stellung nimmt der %-Operator ein, dessen Ergebnis einer Division der ganzzahlige Divisionsrest ist. Dazu ein Beispiel:
    int x = 100;
    int y = 17;
    Console.WriteLine("Division mit % - Ergebnis = {0}", x % y);
Die Zahl 17 ist fünfmal in der Zahl 100 enthalten (für diejenigen, deren Ausbildungsziel der Hochschulreife schon länger als zwei Jahre zurückliegt, ist hier der mathematische Beweis: 5 * 17 = 85), als Rest, der als Ergebnis an der Konsole ausgegeben wird, verbleibt danach 15. Dezimalzahlen als Operanden des %-Operators sind ebenfalls zugelassen, die Rückgabe ist dabei selbst eine Dezimalzahl:
    float x = 100.35;
    float y = 17.45;
    Console.WriteLine("Division mit % - Ergebnis = {0}", x % y);
Wenn Sie diesen Code ausführen, wird im Konsolenfenster die Ausgabe 13,09999 erscheinen. Widmen wir uns jetzt noch einem Beispiel, an dem die Arbeitsweise der Inkrement- bzw. Dekrementoperationen ersichtlich wird. Zunächst betrachten wir das Codefragment einer Postfixinkrementoperation:
    int x = 5;
    int y = x++;
    // y hat den Inhalt 5
Zuerst wird der Variablen x der Wert 5 zugewiesen. Im zweiten Schritt wird der aktuelle Inhalt von x an y übergeben und danach der Inhalt der Variablen x um eins erhöht. Nach Beendigung der zweiten Anweisung weist x den Inhalt 6 auf und y den Inhalt 5. Ein abweichendes Ergebnis erhalten wir, wenn wir den ++-Operator als Präfixinkrementoperator einsetzen.
    int a = 5;
    int b = ++a;
    // b hat den Inhalt 6
In diesem Fall wird zuerst der Inhalt der Variablen a um eins erhöht, und erst danach erfolgt die Zuweisung an die Variable b. Die Folge ist, dass b denselben Inhalt wie a hat. Vielleicht wird Ihnen aufgefallen sein, dass Tabelle 2.6 keinen Potenzoperator beschreibt. Das ist keine Unterlassungssünde des Autors, da C# tatsächlich keinen bereitstellt. Stattdessen gibt es in der .NET-Klassenbibliothek eine Klasse namens Math, die diverse Methoden für mathematische Operationen bereitstellt, unter anderem auch die Methode Pow zum Potenzieren. Wollen Sie beispielsweise das Ergebnis von 25 berechnen, müssen Sie Folgendes codieren:
    double value = Math.Pow(2, 5);
#### Besonderheiten einer Division Bei einer Division zweier ganzer Zahlen gibt es einen Haken, der im ersten Moment nicht offensichtlich ist. Betrachten Sie dazu die beiden folgenden Anweisungen:
    double value = 3 / 4;
    Console.WriteLine(value);
An der Konsole wird nicht, wie zu erwarten wäre, das Ergebnis 0,75 angezeigt, sondern 0. Die Begründung dieses Phänomens ist recht einfach. Zur Laufzeit muss für die beiden Literale 3 und 4 Speicher reserviert werden. Die Laufzeitumgebung erkennt, dass es sich um ganze Zahlen handelt, und interpretiert den Typ der beiden Literale jeweils als Integer. Das Ergebnis der Division wird vor der endgültigen Zuweisung an value zwischengespeichert. Dazu wird Speicher reserviert, der dem Typ des größten der beiden beteiligten Operanden entspricht, mit der Folge, dass der Dezimalteil des Ergebnisses abgeschnitten wird. Bei der anschließenden Zuweisung an value ist das Kind bereits in den Brunnen gefallen – das Ergebnis ist falsch. Zur Lösung dieser Problematik müssen Sie sicherstellen, dass einer der beiden Operanden als Dezimalzahl erkannt wird. Sie können das erreichen, indem Sie beispielsweise
    double value = 3.0 / 4;
codieren. Die Zahl 3 wird jetzt nicht mehr als Integer, sondern als double verarbeitet. Dieser Typ ist erfreulicherweise in der Lage, auch Nachkommastellen aufzunehmen, und das Ergebnis wird korrekt angezeigt. Eine andere Möglichkeit wäre es, einen der Operanden explizit in eine Dezimalzahl zu konvertieren:
    double value = (double)3 / 4;
### 2.4.2 Vergleichsoperatoren Vergleichsoperatoren vergleichen zwei Ausdrücke miteinander. Der Rückgabewert ist immer ein Wahrheitswert, also entweder true oder false. Vergleiche können auf Gleichheit bzw. Ungleichheit sowie auf größer und kleiner durchgeführt werden.

Tabelle 2.7 Vergleichsoperatoren

Operator | Beschreibung
a = = b | Der Vergleichsoperator prüft, ob der Ausdruck a dem Ausdruck b entspricht, und gibt in diesem Fall true zurück.
a != b | Das Ergebnis der Operation ist true, wenn a ungleich b ist.
a > b | Das Ergebnis der Operation ist true, wenn a größer b ist.
a < b | Das Ergebnis der Operation ist true, wenn a kleiner b ist.
a <= b | Das Ergebnis der Operation ist true, wenn a kleiner oder gleich b ist.
a >= b | Das Ergebnis der Operation ist true, wenn a größer oder gleich b ist.
Sehen wir uns einige boolesche Ausdrücke an:
    bool bolCompare;
    bolCompare = intVar <= 100;
Vergleichsoperatoren genießen eine höhere Priorität als der Zuweisungsoperator, daher wird zuerst der Teilausdruck intVar <= 100 ausgewertet. Das Ergebnis des Vergleichs, je nachdem, ob der Vergleich wahr oder falsch ist, wird der Variablen bolCompare zugewiesen. Sie können die boolesche Operation auch direkt zur Initialisierung bei der Deklaration verwenden:
    bool bolCompare = intVar <= 100;
Mit den Vergleichsoperatoren lassen sich auch die Inhalte von zwei string-Variablen miteinander vergleichen:
    string strText1 = "Hallo";
    string strText2 = "hallo";
    bool bolStringCompare = strText1 == strText2;
Der Rückgabewert wird in diesem Fall false sein, weil beim Vergleich von Zeichenketten der Groß-/Kleinschreibung Beachtung geschenkt wird. ### 2.4.3 Logische Operatoren C# bietet eine Reihe logischer Operatoren an, die ebenfalls als Resultat einen booleschen Wert liefern. Sehen wir uns zunächst Tabelle 2.8 an, bevor wir uns an einigen Beispielen die Wirkungsweise dieser Operatoren verdeutlichen.

Tabelle 2.8 Logische Operatoren

Operator | Beschreibung
! | Unärer Negationsoperator: Der Ausdruck !a ist true, wenn a einen unwahren Wert beschreibt, und false, wenn a wahr ist.
& | And-Operator, 1.Variante: Der Ausdruck a & b ist dann true, wenn sowohl a als auch b true sind. Dabei werden in jedem Fall beide Ausdrücke ausgewertet.
| | Or-Operator, 1. Variante: Der Ausdruck a | b ist true, wenn entweder a oder b wahr ist. Dabei werden in jedem Fall beide Ausdrücke ausgewertet.
^ | Xor-Operator: Der Ausdruck a ^ b ist true, wenn die beiden beteiligten Operanden unterschiedliche Wahrheitswerte haben.
&& | And-Operator, 2. Variante: Der Ausdruck a && b ist true, wenn sowohl a als auch b true sind. Zuerst wird a ausgewertet. Sollte a false sein, ist in jedem Fall der Gesamtausdruck unabhängig von b auch falsch. b wird dann nicht mehr ausgewertet.
|| | Or-Operator, 2. Variante: Der Ausdruck a || b ist true, wenn entweder a oder b true ist. Zuerst wird a ausgewertet. Sollte a bereits true sein, ist in jedem Fall der Gesamtausdruck unabhängig von b auch wahr. b wird dann nicht mehr ausgewertet.
Das Ergebnis einer Operation, an der logische Operatoren beteiligt sind, lässt sich am besten anhand einer Wahrheitstabelle darstellen.

Tabelle 2.9 Wahrheitstabellen

Bedingung 1 | Bedingung 2 | And-Operator | Or-Operator | Xor-Operator
false | false | false | false | false
true | false | false | true | true
false | true | false | true | true
true | true | true | true | false
Sehr häufig werden logische Operatoren benutzt, wenn eine Entscheidung darüber getroffen werden muss, welcher Programmcode in Abhängigkeit vom Ergebnis einer Bedingungsprüfung ausgeführt werden soll:
    if(x != y)
      Console.WriteLine("x ist ungleich y");
In diesem einfachen Beispiel, das auch ohne größere Erklärung verständlich sein dürfte, wird die WriteLine-Methode dann ausgeführt, wenn die Bedingung
    x != y
erfüllt ist, also true liefert. Bedingungen können durchaus auch komplexer werden und neben logischen Operatoren auch mehrere Vergleichsoperatoren enthalten. Betrachten wir das folgende Codefragment:
    if(x < 5 || y > 20)
      Console.WriteLine("Bedingung ist erfüllt");
In diesem Codefragment haben wir es mit drei verschiedenen Operatoren zu tun. Da stellt sich sofort die Frage, in welcher Reihenfolge sie zur Bildung des Gesamtergebnisses herangezogen werden. Von den drei Operatoren hat der ||-Operator die geringste Priorität, < und > sind in dieser Hinsicht gleichwertig (siehe auch Abschnitt 2.4.8, »Operator-Vorrangregeln«). Folglich wird zuerst das Ergebnis aus
    x < 5
gebildet und danach das aus:
    y > 20
Beide Teilergebnisse sind entweder true oder false und werden am Schluss mit || verglichen, woraus das Resultat gebildet wird. Manchmal ist es allerdings wegen der besseren Les- und Interpretierbarkeit einer komplexen Bedingung durchaus sinnvoll, auch unnötige Klammerpaare zu setzen:
    if((x < 5) || (y > 20))
Interessant sind insbesondere die ähnlichen Paare & und && bzw. | und ||. Um die Unterschiede in der Verhaltensweise genau zu verstehen, wollen wir ein kleines Beispielprogramm entwickeln, das auch syntaktische Elemente enthält, die bisher noch nicht unser Thema waren.
    // --------------------------------------------------------------
    // Beispiel: ...\Kapitel 2\LogischeOperatoren
    // --------------------------------------------------------------
    using System;
    using System.Collections.Generic;
    using System.Linq;
    using System.Text;
    namespace LogischeOperatoren {
      class Program {
        static void Main(string[] args){
          int x = 8;
          int y = 9;
          // wenn die Bedingung wahr ist, dann dies durch eine
          // Ausgabe an der Konsole bestätigen
          if((x != y) | TestFunction())
            Console.WriteLine("Bedingung ist erfüllt");
          Console.ReadLine();
        }
        // benutzerdefinierte Prozedur
        static bool TestFunction() {
          Console.WriteLine("Aufruf der TestFunction");
          return true;
        }
      }
    }
Neu ist in diesem Beispiel die Definition einer Prozedur, die hier TestFunction heißt. TestFunction macht nicht sehr viel: Sie schreibt nur eine Meldung in das Konsolenfenster und gibt immer den booleschen Wert true als Ergebnis des Aufrufs zurück. In Main werden den beiden Variablen x und y feste Werte zugewiesen. Daraus folgt, dass die Bedingung
    x != y
immer wahr ist. Verknüpft wird diese Bedingung über den Oder-Operator | mit dem Aufruf der benutzerdefinierten Funktion. Da diese einen booleschen Wert zurückliefert, ist der Code syntaktisch korrekt. Führen wir das Programm aus, wird an der Konsole
    Aufruf der TestFunction
    Bedingung ist erfüllt
angezeigt. Halten wir an dieser Stelle die folgende Tatsache fest: Zwei Ausdrücke sind mit dem Oder-Operator | verknüpft. Beide Bedingungen werden vollständig geprüft, bevor das Gesamtergebnis der Operation feststeht. Aus der Wahrheitstabelle (siehe Tabelle 2.9) können wir aber entnehmen, dass die Gesamtbedingung in jedem Fall true ist, wenn einer der beiden Ausdrücke wahr ist. Folglich wäre es auch vollkommen ausreichend, nach dem Prüfen der Bedingung x != y die zweite Bedingung keiner eigenen Überprüfung zu unterziehen, da das Endergebnis bereits feststeht. Hier betritt nun der zweite Oder-Operator (||) die Bühne. Wenn wir die Bedingung nun mit
    if((x != y) || TestFunction())
formulieren, lautet die Ausgabe an der Konsole nur noch:
    Bedingung ist erfüllt
Der Wahrheitsgehalt der zweiten Bedingung wird erst gar nicht mehr überprüft, da er das Endergebnis nicht mehr beeinflussen kann. Genauso arbeiten auch die beiden Operatoren & und &&. In der Praxis kann diesem an sich feinen Unterschied große Bedeutung hinsichtlich der Performance einer Anwendung zukommen. Wenn nämlich die zweite Bedingung eine länger andauernde Ausführungszeit für sich beansprucht und das Ergebnis der ersten Operation die Prüfung der zweiten Bedingung unnötig macht, kann mit || bzw. && durchaus ein kleiner Beitrag zur Verbesserung der Gesamtleistung geleistet werden. ### 2.4.4 Bitweise Operatoren Bitweise Operatoren dienen dazu, auf die Bitdarstellung numerischer Operanden zuzugreifen. Dabei kann die Bitdarstellung eines numerischen Operanden sowohl abgefragt als auch manipuliert werden.

Tabelle 2.10 Bitweise Operatoren

Operator | Beschreibung
~ | Invertiert jedes Bit des Ausdrucks (Einerkomplement).
| | Aus x | y resultiert ein Wert, bei dem die korrespondierenden Bits von x und y Or-verknüpft werden.
& | Aus x & y resultiert ein Wert, bei dem die korrespondierenden Bits von x und y And-verknüpft werden.
^ | Aus x ^ y resultiert ein Wert, bei dem die korrespondierenden Bits von x und y Xor-verknüpft werden.
<< | Aus x << y resultiert ein Wert, der dadurch entsteht, dass die Bits des ersten Operanden x um die durch im zweiten Operanden y angegebene Zahl nach links verschoben werden.
>> | Aus x >> y resultiert ein Wert, der dadurch entsteht, dass die Bits des ersten Operanden x um die durch im zweiten Operanden y angegebene Zahl nach rechts verschoben werden.
Beachten Sie bitte, dass die Operatoren & und | sowohl als Vergleichsoperatoren als auch als bitweise Operatoren eingesetzt werden können. Als Vergleichsoperatoren werden zwei boolesche Operanden miteinander verglichen und ein Wahrheitswert als Ergebnis der Operation zurückgeliefert, und die bitweisen Operatoren vergleichen die einzelnen Bits einer Speicheradresse und bilden daraus das Ergebnis. Wir sehen uns jetzt an einigen Beispielen an, wie diese Operatoren eingesetzt werden können. #### Beispiel 1 Im Folgenden werden die beiden Literale 13 und 5 mit dem bitweisen &-Operator verknüpft:
    a = 13 & 5;
    Console.WriteLine(a);
Die Bitdarstellung dieser beiden Literale sieht wie folgt aus:
    13 = 0000 0000 0000 1101
     5 = 0000 0000 0000 0101
An der Konsole wird als Ergebnis die Zahl 5 angezeigt, was der Bitdarstellung
    0000 0000 0000 0101
entspricht. Wir können unser Ergebnis auch wie folgt interpretieren: Eine vorgegebene Bitsequenz kann mit dem bitweisen &-Operator daraufhin untersucht werden, ob die vom rechten Operanden beschriebenen Bits in der vorgegebenen Bitfolge gesetzt sind. Das ist genau dann der Fall, wenn das Ergebnis der &-Verknüpfung dasselbe Ergebnis liefert wie im rechtsseitigen Operanden angegeben. #### Beispiel 2 Verknüpfen wir nun zwei Literale mit dem bitweisen Oder-Operator |, also beispielsweise:
    int a = 71 | 49;
    Console.WriteLine(a);
Die Bitdarstellung dieser beiden Literale sieht wie folgt aus:
    71 = 0000 0000 0100 0111
    49 = 0000 0000 0011 0001
Das Ergebnis wird 119 lauten oder in Bitdarstellung:
    0000 0000 0111 0111
#### Beispiel 3 Dem Xor-Operator ^ kommt ebenfalls eine ganz besondere Bedeutung zu, wie das folgende Beispiel zeigt:
    int a = 53;
    a = a ^ 22;
    Console.WriteLine(a);
Sehen wir uns zunächst wieder die durch die beiden Literale beschriebenen Bitsequenzen an:
    53 = 0000 0000 0011 0101
    22 = 0000 0000 0001 0110
Lassen wir uns das Ergebnis an der Konsole anzeigen, wird 35 ausgegeben. Das entspricht folgender Bitfolge:
    0000 0000 0010 0011
Hier wird also das zweite, dritte und das fünfte Bit des linken Operanden invertiert – so wie es der rechte Operand vorgibt. Analysieren wir das Ergebnis, kommen wir zu dem folgenden Merksatz:
Merksatz
In einer vorgegebenen Bitsequenz können ganz bestimmte Bits mit dem bitweisen ^-Operator invertiert werden. Die Ausgangsbitfolge steht links vom Operator, und die Zahl, die die Bits repräsentiert, die invertiert werden sollen, steht rechts vom Operator.
Wenden wir auf das Ergebnis ein zweites Mal den ^-Operator an, also
    int a = 53;
    a = a ^ 22;
    a = a ^ 22;
wird die Variable a wieder den ursprünglichen Wert 53 beinhalten. #### Beispiel 4 Zum Abschluss nun noch ein Beispiel mit dem Verschiebeoperator <<. Die Bits des Literals 37 sollen um zwei Positionen nach links verschoben werden, und die Anzeige soll sowohl im Dezimal- als auch im Hexadezimalformat erfolgen.
    c = 37 << 2;
    Console.WriteLine("dezimal    : {0}",c);
    Console.WriteLine("hexadezimal: 0x{0:x}",c);
Die Zahl 37 entspricht der Bitdarstellung:
    0000 0000 0010 0101
Nach der Verschiebung um die geforderten zwei Positionen nach links ergibt sich
    0000 0000 1001 0100
was wiederum der Zahl 148 oder in hexadezimaler Schreibweise 0x94 entspricht, was uns auch die Laufzeitumgebung bestätigt. Mit
    c = 37 >> 2;
lautet das Ergebnis 9, was zu der folgenden Aussage führt: Bei der Bitverschiebung eines positiven Operanden mit dem <<- oder >>-Operator werden die frei werdenden Leerstellen mit 0-Bits aufgefüllt. ### 2.4.5 Zuweisungsoperatoren Bis auf die Ausnahme des einfachen Gleichheitszeichens dienen alle anderen Zuweisungsoperatoren zur verkürzten Schreibweise einer Anweisung, bei der der linke Operand einer Operation gleichzeitig auch der Empfänger des Operationsergebnisses ist.

Tabelle 2.11 Zuweisungsoperatoren

Operator | Beschreibung
= | x = y weist x den Wert von y zu.
+= | x += y weist x den Wert von x + y zu.
-= | x -= y weist x den Wert von x – y zu.
*= | x *= y weist x den Wert von x * y zu.
/= | x /= y weist x den Wert von x / y zu.
%= | x %= y weist x den Wert von x % y zu.
&= | x &= y weist x den Wert von x & y zu.
|= | x |= y weist x den Wert von x | y zu.
^= | x ^= y weist x den Wert von x ^ y zu.
<<= | x <<= y weist x den Wert von x << y zu.
>>= | x >>= y weist x den Wert von x >> y zu.
### 2.4.6 Stringverkettung Den +-Operator haben Sie bereits in Verbindung mit arithmetischen Operationen kennengelernt. Ihm kommt allerdings auch noch eine zweite Aufgabe zu, nämlich die Verkettung von Zeichenfolgen. Ist wenigstens einer der beiden an der Operation beteiligten Operanden vom Typ string, bewirkt der +-Operator eine Stringverkettung. Bei Bedarf wird der Operand, der nicht vom Typ string ist, implizit in einen solchen konvertiert. Das Ergebnis der Stringverkettung ist wieder eine Zeichenfolge. Nachfolgend finden Sie einige Codefragmente, die Beispiele für Stringverkettungen zeigen.
    string strText1 = "Leckere";
    string strText2 = "Suppe";
    string strText3 = strText1 + " " + strText2;
    // strText3 hat den Inhalt 'Leckere Suppe'
    int intVar = 4711;
    string strText = "Hallo";
    strText += intVar;
    // strText hat den Inhalt 'Hallo4711'
    string strInt1 = "4";
    string strInt2 = "3";
    Console.WriteLine(strInt1 + strInt2);
    // strText hat den Inhalt '43'
### 2.4.7 Sonstige Operatoren Wir sind noch nicht am Ende der Aufzählung der Operatoren von C# angelangt. Es stehen Ihnen noch einige besondere Operatoren zur Verfügung, mit denen Sie in den vorhergehenden Abschnitten teilweise auch schon gearbeitet haben oder die Sie im weiteren Verlauf dieses Buches noch kennenlernen werden. Der Vollständigkeit halber sind die Operatoren dieser Gruppe in Tabelle 2.12 aufgeführt.

Tabelle 2.12 Sonstige C#-Operatoren

Operator | Beschreibung
. | Der Punktoperator wird für den Zugriff auf die Eigenschaften oder Methoden einer Klasse verwendet, z. B. Console.ReadLine();.
[] | Der []-Operator wird für Arrays, Indexer und Attribute verwendet, z. B. arr[10].
() | Der ()-Operator dient zwei Zwecken: Er gibt die Reihenfolge der Operationen vor und wird auch zur Typkonvertierung eingesetzt.
?: | Der ?:-Operator gibt einen von zwei Werten in Abhängigkeit von einem dritten zurück. Er ist eine einfache Variante der if-Bedingungsprüfung.
new | Dient zur Instanziierung einer Klasse.
is | Prüft den Laufzeittyp eines Objekts mit einem angegebenen Typ.
typeof | Ruft das System.Type-Objekt für einen Typ ab.
checked / unchecked | Steuert die Reaktion der Laufzeitumgebung bei einem arithmetischen Überlauf.
### 2.4.8 Operator-Vorrangregeln Enthält ein Ausdruck mehrere Operatoren, entscheiden die Operator-Vorrangregeln über die Reihenfolge der Ausführung der einzelnen Operationen. In Tabelle 2.13 sind die Operatoren so angeordnet, dass die weiter oben stehenden Vorrang vor den weiter unten stehenden haben.

Tabelle 2.13 Operator-Vorrangregeln

Gruppe | Operator
1 | x.y (Punktoperator), a[x], x++, x--, new, typeof, checked, unchecked
2 | + (unär), - (unär), !, ~, ++x, --x, (<Typ>)x
3 | *, /, %
4 | + (additiv), - (subtraktiv)
5 | <<, >>
6 | <, >, <=, >=, is
7 | ==, !=
8 | &
9 | ^
10 | |
11 | &&
12 | ||
13 | ?:
14 | =, *=, /=, %=, +=, -=, <<=, >>=, &=, ^=, |=