Variablen in Java
Lerne alles über Variablen in Java: Deklaration, Initialisierung, Scope, finale Variablen und den Unterschied zwischen primitiven und Referenztypen.
Variablen in Java
Variablen sind das Fundament jedes Programms. Sie sind wie beschriftete Boxen, in denen du Daten speichern, veraendern und wieder abrufen kannst. In Java gibt es dabei ein paar Besonderheiten, die du kennen solltest.
Variablen deklarieren und initialisieren
In Java musst du beim Erstellen einer Variable den Typ angeben:
// Deklaration (Variable anlegen)
int alter;
// Initialisierung (Wert zuweisen)
alter = 25;
// Deklaration + Initialisierung in einem Schritt
int gewicht = 75;
String name = "Max";
double groesse = 1.82;
boolean istStudent = true;
Mit var (Typinferenz seit Java 10)
Mit var erkennt Java den Typ automatisch:
var alter = 25; // int
var name = "Max"; // String
var groesse = 1.82; // double
var istStudent = true; // boolean
var liste = List.of(1, 2, 3); // List<Integer>
Wichtig: var funktioniert nur bei lokalen Variablen (innerhalb von Methoden) und nur, wenn du sofort einen Wert zuweist.
// GEHT:
var x = 42;
// GEHT NICHT:
var y; // Fehler! Kein Wert zugewiesen
y = 42;
Vergleich mit Python
# Python: Typ wird automatisch erkannt, kann sich aendern
name = "Max"
name = 42 # Kein Fehler! Typ aendert sich
// Java: Typ ist fest
var name = "Max";
name = 42; // FEHLER! name ist ein String, kein int
In Java ist der Typ einer Variable unveraenderlich — einmal String, immer String.
Variablen-Typen in Java
Lokale Variablen
Lokale Variablen existieren nur innerhalb einer Methode oder eines Blocks:
public static void main(String[] args) {
var nachricht = "Hallo"; // Lokale Variable
System.out.println(nachricht);
} // nachricht existiert hier nicht mehr
Instanzvariablen (Felder)
Instanzvariablen gehoeren zu einem Objekt:
public class Student {
String name; // Instanzvariable
int matrikelnummer; // Instanzvariable
public void vorstellen() {
System.out.println("Ich bin " + name);
}
}
Klassenvariablen (static)
Klassenvariablen gehoeren zur Klasse selbst, nicht zu einzelnen Objekten:
public class Zaehler {
static int anzahl = 0; // Klassenvariable
public Zaehler() {
anzahl++;
}
}
Konstanten (final)
Mit final erstellst du Variablen, deren Wert sich nicht mehr aendern kann:
final double PI = 3.14159265;
final String FIRMENNAME = "MeineFirma GmbH";
final int MAX_VERSUCHE = 3;
PI = 3.0; // FEHLER! final-Variable kann nicht geaendert werden
Konvention: Konstanten werden in UPPER_SNAKE_CASE geschrieben.
public class Einstellungen {
public static final int MAX_SPIELER = 10;
public static final String VERSION = "2.0.1";
public static final double MEHRWERTSTEUER = 0.19;
}
Scope (Gueltigkeitsbereich)
Der Scope bestimmt, wo eine Variable sichtbar und nutzbar ist:
public class ScopeBeispiel {
static int klassenVariable = 100; // Ueberall in der Klasse
public static void main(String[] args) {
var aussen = "Ich bin aussen"; // Sichtbar in der ganzen Methode
if (true) {
var innen = "Ich bin innen"; // Nur im if-Block sichtbar
System.out.println(aussen); // OK
System.out.println(innen); // OK
}
System.out.println(aussen); // OK
// System.out.println(innen); // FEHLER! innen existiert hier nicht
}
}
Scope-Regeln
| Regel | Erlaeuterung |
|---|---|
Variablen sind nur in ihrem Block {} sichtbar | Nach der schliessenden Klammer sind sie weg |
| Aeussere Variablen sind in inneren Bloecken sichtbar | Aber nicht umgekehrt |
| Variablen im selben Scope duerfen nicht gleich heissen | Kompilierfehler! |
// Shadowing: Aeussere Variable wird "verdeckt"
public static void main(String[] args) {
var x = 10;
if (true) {
// var x = 20; // FEHLER in Java! Lokale Variable kann nicht verdeckt werden
x = 20; // OK -- gleiche Variable, neuer Wert
}
System.out.println(x); // 20
}
Variablen veraendern
Zuweisungsoperatoren
var punkte = 100;
punkte = 200; // Direkte Zuweisung
punkte += 50; // punkte = punkte + 50 --> 250
punkte -= 30; // punkte = punkte - 30 --> 220
punkte *= 2; // punkte = punkte * 2 --> 440
punkte /= 4; // punkte = punkte / 4 --> 110
punkte %= 3; // punkte = punkte % 3 --> 2
System.out.println(punkte); // 2
Inkrement und Dekrement
var zaehler = 10;
zaehler++; // zaehler = zaehler + 1 --> 11
zaehler--; // zaehler = zaehler - 1 --> 10
// Praefix vs. Postfix
var a = 5;
var b = a++; // b = 5, dann a = 6 (erst zuweisen, dann erhoehen)
var c = ++a; // a = 7, dann c = 7 (erst erhoehen, dann zuweisen)
Primitive vs. Referenztypen
Das ist einer der wichtigsten Unterschiede in Java:
Primitive Typen — Werte direkt gespeichert
int a = 42;
int b = a; // b bekommt eine KOPIE des Werts
b = 100; // a bleibt 42!
System.out.println(a); // 42
System.out.println(b); // 100
Referenztypen — Referenz auf ein Objekt
int[] a = {1, 2, 3};
int[] b = a; // b zeigt auf das GLEICHE Array!
b[0] = 999; // Aendert auch a!
System.out.println(a[0]); // 999 -- Ueberraschung!
Visualisierung
Primitive:
a: [42] b: [42] // Zwei getrennte Boxen
Referenz:
a: [Ref] ──┐
├──> [1, 2, 3] // Beide zeigen auf dasselbe Objekt
b: [Ref] ──┘
Typkonvertierung (Casting)
Implizite Konvertierung (Widening)
Java wandelt automatisch um, wenn kein Datenverlust moeglich ist:
int ganzzahl = 42;
double dezimal = ganzzahl; // int --> double: kein Datenverlust
System.out.println(dezimal); // 42.0
Reihenfolge: byte -> short -> int -> long -> float -> double
Explizite Konvertierung (Narrowing/Casting)
Wenn Datenverlust moeglich ist, musst du explizit casten:
double dezimal = 3.99;
int ganzzahl = (int) dezimal; // Expliziter Cast
System.out.println(ganzzahl); // 3 -- Nachkommastellen abgeschnitten!
String-Konvertierung
// Zahl zu String
var zahlAlsString = String.valueOf(42); // "42"
var zahlAlsString2 = Integer.toString(42); // "42"
var zahlAlsString3 = "" + 42; // "42" (einfachste Variante)
// String zu Zahl
var zahl = Integer.parseInt("42"); // 42
var dezimal = Double.parseDouble("3.14"); // 3.14
Default-Werte
Instanzvariablen bekommen automatisch Default-Werte. Lokale Variablen nicht — du musst sie initialisieren:
| Typ | Default-Wert |
|---|---|
int, long, short, byte | 0 |
double, float | 0.0 |
boolean | false |
char | '\u0000' (Null-Zeichen) |
| Referenztypen (String, Arrays, etc.) | null |
public class DefaultWerte {
int zahl; // 0
String text; // null
boolean aktiv; // false
public static void main(String[] args) {
// var x; // FEHLER! Lokale Variable muss initialisiert werden
var x = 0; // OK
}
}
Best Practices
1. Sinnvolle Namen verwenden
// SCHLECHT:
int x = 25;
String s = "Max";
double d = 1.82;
// GUT:
int alter = 25;
String vorname = "Max";
double koerpergroesse = 1.82;
2. Variablen so spaet wie moeglich deklarieren
// SCHLECHT:
var ergebnis = 0.0;
var eingabe = "";
// ... 50 Zeilen Code ...
eingabe = scanner.nextLine();
ergebnis = berechne(eingabe);
// GUT:
// ... 50 Zeilen Code ...
var eingabe = scanner.nextLine();
var ergebnis = berechne(eingabe);
3. final nutzen, wenn der Wert sich nicht aendert
// Wenn sich der Wert nie aendert: final
final var steuerSatz = 0.19;
final var firmenName = "TechCorp";
Uebungen
Uebung 1: Variablen tauschen
Schreibe ein Programm, das die Werte zweier Variablen tauscht, ohne eine dritte Variable zu verwenden (Tipp: Addition und Subtraktion).
Uebung 2: Typkonvertierung
Erstelle eine Variable vom Typ double mit dem Wert 9.99. Konvertiere sie in einen int und dann in einen String. Gib alle drei Werte aus.
Uebung 3: Scope verstehen
Was gibt das folgende Programm aus? Ueberlege erst, dann pruefe:
var x = 10;
if (x > 5) {
var y = 20;
x = x + y;
}
System.out.println(x);
// System.out.println(y); // Was passiert hier?
Uebung 4: Konstanten-Rechner
Erstelle ein Programm mit Konstanten fuer PI, die Lichtgeschwindigkeit (299792458 m/s) und die Erdbeschleunigung (9.81 m/s^2). Berechne damit den Umfang eines Kreises mit Radius 5.
Was kommt als Naechstes?
In der naechsten Lektion schauen wir uns die primitiven Datentypen im Detail an. Du lernst die Unterschiede zwischen int, long, double, float und den anderen Typen — und wann du welchen verwenden solltest.
Zusammenfassung
- Variablen brauchen in Java einen festen Typ (
int,String, etc.) odervar - Lokale Variablen leben in Methoden, Instanzvariablen in Objekten
finalmacht eine Variable unveraenderbar (Konstante)- Der Scope bestimmt, wo eine Variable sichtbar ist
- Primitive Typen speichern Werte direkt, Referenztypen speichern Referenzen
- Casting konvertiert zwischen Typen (
(int) 3.14ergibt3) - Verwende sprechende Namen und deklariere Variablen so spaet wie moeglich
Pro-Tipp: Nutze var fuer lokale Variablen, wenn der Typ aus dem Kontext klar ist: var liste = new ArrayList<String>() ist lesbarer als ArrayList<String> liste = new ArrayList<String>(). Aber bei var result = getResult() ist unklar, welchen Typ result hat — dann schreibe den Typ lieber explizit hin.