Top-Fehler von Java-Anfängern: Fortgeschrittenes Niveau
Viele Entwickler, die die Grundlagen von Java beherrschen, gehen dazu über, komplexeren Code zu schreiben, machen aber weiterhin typische Fehler, die die Leistung und Zuverlässigkeit von Anwendungen beeinträchtigen. In diesem Artikel analysieren wir die häufigsten Fehler auf fortgeschrittenem Niveau, die bei Java-Entwicklern auftreten, und zeigen, wie man sie vermeidet. Der Artikel ist nützlich für diejenigen, die bereits mit der Syntax der Sprache vertraut sind, aber ihr Wissen vertiefen möchten.
1. Falsche Verwendung von Optional
Die Klasse Optional wurde in Java 8 eingeführt, um NullPointerException zu bekämpfen. Viele Entwickler verwenden sie jedoch falsch und verwandeln eine elegante Lösung in eine Quelle neuer Probleme.
Fehler: Verwendung von Optional.get() ohne Prüfung
Einer der häufigsten Fehler ist der Aufruf der Methode get() ohne vorherige Prüfung mit isPresent(). Dies führt zu einer NoSuchElementException.
// FalschOptional<String> name = Optional.ofNullable(getName());String result = name.get(); // Exception, wenn name == null
// RichtigString result = name.orElse("Default");// Oder mit Verarbeitungname.ifPresent(System.out::println);Fehler: Verwendung von Optional in Klassenfeldern
Optional ist nicht für die Verwendung als Klassenfeld oder Methodenparameter vorgesehen. Dies verletzt die Serialisierung und fügt unnötige Komplexität hinzu.
// Falschpublic class User { private Optional<String> email; // Nicht serialisierbar}
// Richtigpublic class User { private String email; // null bedeutet Abwesenheit}Fehler: Optional.orElse()-Ketten mit teuren Berechnungen
Die Methode orElse() berechnet das Argument immer, auch wenn der Wert vorhanden ist. Verwenden Sie orElseGet() für faule Berechnungen.
// Falsch — expensiveCall() wird immer ausgeführtString result = optional.orElse(expensiveCall());
// Richtig — expensiveCall() wird nur ausgeführt, wenn der Wert fehltString result = optional.orElseGet(() -> expensiveCall());2. Speicherlecks und falsche Arbeit mit Collections
Fortgeschrittene Entwickler stoßen oft auf Speicherlecks, die schwer zu erkennen sind. Betrachten wir die Hauptursachen.
Fehler: Vergessen, equals() und hashCode() zu überschreiben
Bei der Verwendung von Objekten in HashMap oder HashSet ohne korrekte equals() und hashCode() werden Objekte nicht aus der Collection entfernt, was zu Speicherlecks führt.
public class Key { private int id; // Vergessen, equals() und hashCode() zu überschreiben // Jetzt werden Schlüssel als unterschiedlich betrachtet, selbst wenn die id übereinstimmt}
Map<Key, String> map = new HashMap<>();map.put(new Key(1), "value");map.get(new Key(1)); // null — SpeicherleckFehler: Speichern großer Objekte in static Collections
Statische Collections leben bis zum Ende der Anwendung. Wenn ihnen ohne Kontrolle Daten hinzugefügt werden, führt dies zu OutOfMemoryError.
// Schlechte Praxispublic class CacheManager { private static List<byte[]> cache = new ArrayList<>(); public static void addData(byte[] data) { cache.add(data); // Wächst unendlich }}
// Lösung: Verwenden Sie WeakHashMap oder begrenzen Sie die Größeprivate static Map<String, byte[]> cache = new WeakHashMap<>();Fehler: Schließen von Ressourcen über finalize()
Die Methode finalize() ist veraltet und unzuverlässig. Verwenden Sie try-with-resources zum automatischen Schließen.
// Falschpublic class Resource { @Override protected void finalize() throws Throwable { // Ressource schließen — kann unaufgerufen bleiben