Java Standard: Operatoren
Welche Operatoren gibt es in Java?
[Bearbeiten]Java kennt eine Vielzahl von arithmetischen, logischen, und relationalen Operatoren, sowie einen, der außerhalb von Java keine Rolle spielt. Operatoren werden nach der Anzahl der möglichen Operanden unterteilt (unärer-, binärer- und ternärer Operator) und selbstverständlich nach der Funktion, die sie berechnen. Dieses Kapitel beschreibt die verfügbaren Operatoren in Tabellenform. Bis auf wenige Ausnahmen sollten alle Operatoren und das, was sie leisten, aus der Schule bekannt sein.
Arithmetische Operatoren
[Bearbeiten]Operator | Beschreibung | Kurzbeispiel |
---|---|---|
+ | Addition | int antwort = 40 + 2;
|
- | Subtraktion | int antwort = 48 - 6;
|
* | Multiplikation | int antwort = 2 * 21;
|
/ | Division | int antwort = 84 / 2;
|
% | Teilerrest, Modulo-Operation, errechnet den Rest einer Division | int antwort = 99 % 57;
|
+ | positives Vorzeichen, in der Regel überflüssig | int j = +3;
|
- | negatives Vorzeichen | int minusJ = -j;
|
Für zwei besonders in Schleifen häufig anzutreffende Berechnungen gibt es eine abkürzende Schreibweise.
Operator | Beschreibung | Kurzbeispiel |
---|---|---|
++ | Postinkrement, Addiert 1 zu einer numerischen Variablen | x++;
|
++ | Preinkrement, Addiert 1 zu einer numerischen Variablen | ++x;
|
-- | Postdekrement, Subtrahiert 1 von einer numerischen Variablen | x--;
|
-- | Predekrement, Subtrahiert 1 von einer numerischen Variablen | --x;
|
Post- und Pre-Operatoren verhalten sich bezüglich ihrer Berechnung absolut gleich, der Unterschied ist der Zeitpunkt, wann die Operation ausgeführt wird. Zum Tragen kommt das bei Zuweisungen:
i = 1;
a = ++i; // i = 2 und a = 2 (erst hochzählen, dann zuweisen)
i = 1;
b = i++; // i = 2 und b = 1 (erst zuweisen, dann hochzählen)
Operatoren für Vergleiche
[Bearbeiten]Das Ergebnis dieser Operationen ist aus der Menge true
, false
:
Operator | Beschreibung | Kurzbeispiel |
---|---|---|
== | gleich | 3 == 3
|
!= | ungleich | 4 != 3
|
> | größer als | 4 > 3
|
< | kleiner als | -4 < -3
|
>= | größer als oder gleich | 3 >= 3
|
<= | kleiner als oder gleich | -4 <= 4
|
Boolesche Operatoren
[Bearbeiten]Operator | Beschreibung | Kurzbeispiel |
---|---|---|
! | Negation, invertiert den Ausdruck | boolean lügnerSpricht = !wahrheit;
|
&& | Und, true , genau dann wenn alle Argumente true sind |
boolean krümelmonster = istBlau && magKekse;
|
|| | or true , wenn mindestens ein Operand true ist |
boolean machePause = hungrig || durstig;
|
^ | Xor true wenn genau ein Operand true ist |
boolean zustandPhilosoph = denkt ^ ist;
|
Operatoren zur Manipulation von Bits
[Bearbeiten]Operator | Beschreibung | Kurzbeispiel |
---|---|---|
~ | (unäre) invertiert alle Bits seines Operanden | 0b10111011 = ~0b01000100
|
& | bitweises "und", wenn beide Operanden 1 sind, wird ebenfalls eine 1 produziert, ansonsten eine 0 | 0b10111011 = 0b10111111 & 0b11111011
|
| | bitweises "oder", produziert eine 1, sobald einer seiner Operanden eine 1 ist | 0b10111011 = 0b10001000 | 0b00111011
|
^ | bitweises "exklusives oder", wenn beide Operanden den gleichen Wert haben, wird eine 0 produziert, ansonsten eine 1 | 0b10111011 = 0b10001100 ^ 0b00110111
|
Operator | Beschreibung | Kurzbeispiel |
---|---|---|
>> | Arithmetischer Rechtsshift: Rechtsverschiebung, alle Bits des Operanden werden um eine Stelle nach rechts verschoben, stand ganz links eine 1 wird mit einer 1 aufgefüllt, bei 0 wird mit 0 aufgefüllt | 0b11101110 = 0b10111011 >> 2
|
>>> | Logischer Rechtsshift: Rechtsverschiebung mit Auffüllung von Nullen | 0b00101110 = 0b01011101 >>> 1
|
<< | Linksverschiebung, entspricht bei positiven ganzen Zahlen einer Multiplikation mit 2, sofern keine "1" rausgeschoben wird. | 0b10111010 = 0b01011101 << 1
|
Zuweisungsoperatoren
[Bearbeiten]Zu vielen Operatoren aus den vorstehenden Tabellen gehört eine Schreibweise, mit der gleichzeitig zugewiesen werden kann. Damit spart man sich oft etwas Schreibarbeit. Also, statt etwa x = x * 7;
zu schreiben kann man etwas verkürzt schreiben: x *= 7;
.
Operator | Beschreibung | Kurzbeispiel |
---|---|---|
= | einfache Zuweisung | int var = 7;
|
+= | Addiert einen Wert zu der angegebenen Variablen | plusZwei += 2;
|
-= | Subtrahiert einen Wert von der angegebenen Variablen | minusZwei -= 2;
|
/= | Dividiert die Variable durch den angegebenen Wert und weist ihn zu | viertel /= 4;
|
*= | Multipliziert die Variable mit dem angegebenen Wert und weist ihn zu | vierfach *= 4;
|
%= | Ermittelt den Modulo einer Variablen und weist ihn der Variablen zu | restModulo11 %= 11;
|
&= | "und"-Zuweisung | maskiert &= bitmaske;
|
|= | "oder"-Zuweisung | |
^= | "exklusives oder"-Zuweisung | |
^= | bitweise "exklusive oder"-Zuweisung | |
>>= | Rechtsverschiebungzuweisung | |
>>>= | Rechtsverschiebungzuweisung mit Auffüllung von Nullen | |
<<= | Linksverschiebungzuweisung | achtfach <<= 3;
|
Bedingungsoperator
[Bearbeiten]Den einzigen ternären Operator ?:
stellen wir im Kapitel Kontrollstrukturen vor.
Konkatenation
[Bearbeiten]Zwei String
s lassen sich mit "+" aneinanderschreiben, so wie Sie es schon aus früheren System.out.println("Hallo" + " Welt" + "!");
-Beispielen kennen.
Rangfolge von Operatoren
[Bearbeiten]Die Rangfolge der Operatoren (engl. "operator precedence" oder auch "precedence rules") bestimmt in der Regel[1], in welcher Reihenfolge sie ausgewertet werden. Es geht darum, Klammern zu sparen. Weiß man, dass &&
einen höheren Rang als ||
hat, dann wird der Ausdruck (A && B) || C
zu A && B || C
. Selbstverständlich darf man trotzdem Klammern setzen.
Ganz allgemein gilt, dass Ausdrücke von links nach rechts ausgewertet werden. Das gilt nicht für Zuweisungsoperatoren.
In der folgenden Tabelle[2] werden die Operatoren und ihre Ränge aufgeführt. Je weiter oben ein Operator in der Tabelle auftaucht, desto eher wird er ausgewertet. Operatoren mit dem gleichen Rang (in der gleichen Zeile) werden von links nach rechts ausgewertet.
Rangfolge | Typ | Operatoren |
---|---|---|
1 | Postfix-Operatoren, Postinkrement, Postdekrement | x++ , x--
|
2 | Einstellige (unäre) Operatoren, Vorzeichen | ++x , --x , +x , -x , ~b , !b
|
3 | Multiplikation, Teilerrest | a*b , a/b , a % b
|
4 | Addition, Subtraktion | a + b , a - b
|
5 | Bitverschiebung | d << k , d >> k , d >>> k
|
6 | Vergleiche | a < b , a > b , a <= b , a >= b , s instanceof S
|
7 | Gleich, Ungleich | a == b , a != b
|
8 | UND (Bits) | b & c
|
9 | Exor (Bits) | b ^ c
|
10 | ODER (Bits) | b | c
|
11 | Logisch UND | B && C
|
12 | Logisch ODER | B || C
|
13 | Bedingungsoperator | a ? b : c
|
14 | Zuweisungen | a = b , a += 3 , a -= 3 , a *= 3 , a /= 3 , a %= 3 , b &= c , b ^= c , b |= c , d <<=k , d >>= k , d >>>= k
|
- ↑ siehe nächsten Abschnitt Fallen
- ↑ Zum Teil entnommen von https://docs.oracle.com/javase/tutorial/java/nutsandbolts/operators.html
Fallen
[Bearbeiten]Es gibt zum Glück wenig Fallstricke im Gebrauch von Operatoren. Postfix-Operatoren werden immer zuerst nach dem aktuellen Wert, den sie haben ausgewertet, erst dann erfolgt die Operation darauf.
Nicht in allen Fällen kann man sich bei Beachtung der Rangfolge Klammern sparen. Versuchen Sie doch einmal, den Ausdruck int x = ++y++;
auszuwerten (wobei y
vorher deklariert wurde). Trotz der klaren Vorrangregeln lässt sich dieser Ausdruck nicht kompilieren. Gut für alle, die einen solchen Quelltext lesen müssen...
Für weitere schwer zu durchschauende Fallen siehe auch Strukturierte Programmierung / Komplexe Ausdrücke.
Rechengenauigkeit
[Bearbeiten]Beim Rechnen mit zwei Datentypen unterschiedlicher Genauigkeit (z.B. int
und long
) muss beachtet werden, dass als Ergebnis der "genaue" Datentyp berechnet wird.
long = int + long;
Wird nur ein "ungenauerer" Wert benötigt, so muss das dem Compiler mitgeteilt werden (cast
).
int = (int) (int + long);
Die Genauigkeit ist hier durch den Zahl gegeben. Ein Datentyp int kann eine 32-Bit-Ganzzahl darstellen, während der Typ long 64-Bit-Ganzzahlen aufnehmen kann (= 8 Byte). Deshalb "passt" ein int-Wert problemlos in einen long-Wert. Umgekehrt kann es da schon passieren, dass der long-Wert größer als der größtmögliche int-Wert ausfällt!