Namensräume
Varianten
Aktionen

C Operator-Rangfolge

Von cppreference.com
< c‎ | Sprache

Die folgende Tabelle listet die Rangfolge und Assoziativität von C-Operatoren auf. Operatoren sind von oben nach unten in absteigender Rangfolge aufgeführt.

Rangfolge Operator Beschreibung Assoziativität
1 ++ -- Suffix-/Post-Inkrement und -Dekrement Links nach rechts
() Funktionsaufruf
[] Array-Indizierung
. Zugriff auf Struktur- und Union-Member
-> Zugriff auf Struktur- und Union-Member über Zeiger
(Typ){Liste} Compound Literal(C99)
2 ++ -- Präfix-Inkrement und -Dekrement[Anm. 1] Rechts nach links
+ - Unäres Plus und Minus
! ~ Logisches NICHT und bitweises NICHT
(Typ) Typumwandlung (Cast)
* Indirektion (Dereferenzierung)
& Adress-Operator
sizeof Größe von[Anm. 2]
_Alignof Ausrichtungsanforderung(C11)
3 * / % Multiplikation, Division und Rest Links nach rechts
4 + - Addition und Subtraktion
5 << >> Bitweises Links- und Rechts-Shift
6 < <= Für relationale Operatoren < bzw. ≤
> >= Für relationale Operatoren > bzw. ≥
7 == != Für relationale Operatoren = bzw. ≠
8 & Bitweises UND
9 ^ Bitweises XOR (exklusives ODER)
10 | Bitweises ODER (inklusives ODER)
11 && Logisches UND
12 || Logisches ODER
13 ?: Ternärer bedingter Operator[Anm. 3] Rechts nach links
14[Anm. 4] = Einfache Zuweisung
+= -= Zuweisung durch Summe und Differenz
*= /= %= Zuweisung durch Produkt, Quotient und Rest
<<= >>= Zuweisung durch bitweises Links- und Rechts-Shift
&= ^= |= Zuweisung durch bitweises AND, XOR und OR
15 , Komma Links nach rechts
  1. Der Operand von Präfix ++ und -- darf kein Typ-Cast sein. Diese Regel verbietet grammatikalisch einige Ausdrücke, die ohnehin semantisch ungültig wären. Einige Compiler ignorieren diese Regel und erkennen die Ungültigkeit semantisch.
  2. Der Operand von sizeof darf kein Typ-Cast sein: Der Ausdruck sizeof (int) * p wird eindeutig als (sizeof(int)) * p interpretiert und nicht als sizeof((int)*p).
  3. Der Ausdruck in der Mitte des bedingten Operators (zwischen ? und :) wird so geparst, als ob er in Klammern stünde: seine Rangfolge relativ zu ?: wird ignoriert.
  4. Linke Operanden von Zuweisungsoperatoren müssen unäre (Rangfolge 2, nicht-Cast) Ausdrücke sein. Diese Regel verbietet grammatikalisch einige Ausdrücke, die ohnehin semantisch ungültig wären. Viele Compiler ignorieren diese Regel und parsen sie semantisch. Zum Beispiel ist e = a < d ? a++ : a = d ein Ausdruck, der aufgrund dieser Regel nicht geparst werden kann. Viele Compiler ignorieren diese Regel jedoch und parsen ihn als e = ( ((a < d) ? (a++) : a) = d ) und geben dann einen Fehler aus, da er semantisch ungültig ist.

Beim Parsen eines Ausdrucks wird ein Operator, der in einer Zeile aufgeführt ist, fester (als ob durch Klammern) an seine Argumente gebunden als jeder Operator, der in einer darunter liegenden Zeile aufgeführt ist. Zum Beispiel wird der Ausdruck *p++ als *(p++) geparst und nicht als (*p)++.

Operatoren, die sich in derselben Zelle befinden (es können mehrere Zeilen von Operatoren in einer Zelle aufgeführt sein), werden mit derselben Rangfolge in der angegebenen Richtung ausgewertet. Zum Beispiel wird der Ausdruck a=b=c als a=(b=c) geparst und nicht als (a=b)=c, aufgrund der Rechts-nach-links-Assoziativität.

[bearbeiten] Anmerkungen

Rangfolge und Assoziativität sind unabhängig von der Auswertungsreihenfolge.

Der Standard selbst gibt keine Rangfolgen an. Sie leiten sich aus der Grammatik ab.

In C++ hat der bedingte Operator die gleiche Rangfolge wie Zuweisungsoperatoren, und Präfix-++ und -- sowie Zuweisungsoperatoren haben nicht die Einschränkungen bezüglich ihrer Operanden.

Die Angabe der Assoziativität ist für unäre Operatoren redundant und dient nur der Vollständigkeit: unäre Präfix-Operatoren assoziieren immer von rechts nach links (sizeof ++*p ist sizeof(++(*p))) und unäre Postfix-Operatoren assoziieren immer von links nach rechts (a[1][2]++ ist ((a[1])[2])++). Beachten Sie, dass die Assoziativität für Member-Zugriffsoperatoren bedeutsam ist, obwohl sie mit unären Postfix-Operatoren gruppiert sind: a.b++ wird als (a.b)++ geparst und nicht als a.(b++).

[bearbeiten] Referenzen

  • C17-Standard (ISO/IEC 9899:2018)
  • A.2.1 Ausdrücke
  • C11-Standard (ISO/IEC 9899:2011)
  • A.2.1 Ausdrücke
  • C99-Standard (ISO/IEC 9899:1999)
  • A.2.1 Ausdrücke
  • C89/C90-Standard (ISO/IEC 9899:1990)
  • A.1.2.1 Ausdrücke

[bearbeiten] Siehe auch

Auswertungsreihenfolge von Operatorargumenten zur Laufzeit.

Häufige Operatoren
Zuweisung Inkrement
Dekrement
Arithmetik Logisch Vergleich Member
Zugriff
Sonstiges

a = b
a += b
a -= b
a *= b
a /= b
a %= b
a &= b
a |= b
a ^= b
a <<= b
a >>= b

++a
--a
a++
a--

+a
-a
a + b
a - b
a * b
a / b
a % b
~a
a & b
a | b
a ^ b
a << b
a >> b

!a
a && b
a || b

a == b
a != b
a < b
a > b
a <= b
a >= b

a[b]
*a
&a
a->b
a.b

a(...)
a, b
(type) a
a ? b : c
sizeof


_Alignof
(seit C11)
(bis C23)

alignof
(seit C23)

C++-Dokumentation für C++ Operator-Rangfolge