CodeGym/Java-Blog/Random-DE/Erkundung der Fragen und Antworten aus einem Vorstellungs...
John Squirrels
Level 41
San Francisco

Erkundung der Fragen und Antworten aus einem Vorstellungsgespräch für eine Stelle als Java-Entwickler. Teil 2

Veröffentlicht in der Gruppe Random-DE
Hallo nochmal, alle zusammen! Wir suchen weiterhin nach Antworten auf Fragen für Junior-, Mid-Level- und Senior-Java-Entwickler. Die Fragen sind super interessant. Ich persönlich analysiere sie gerne, weil es mir hilft, Lücken in meinem theoretischen Wissen zu finden, und zwar manchmal an den unerwartetsten Stellen. Erkundung der Fragen und Antworten aus einem Vorstellungsgespräch für eine Stelle als Java-Entwickler.  Teil 2 - 1Den vorherigen Teil finden Sie in diesem Artikel . Aber bevor wir beginnen, möchte ich Sie daran erinnern:
  1. Ich werde die Fragen, die sich mit dieser Artikelserie überschneiden, überspringen , um die Informationen nicht unnötig zu duplizieren. Ich empfehle die Lektüre dieser Artikel, da sie die häufigsten (beliebtesten) Java Core-Interviewfragen behandeln.
  2. Ich könnte die Antworten ausführlicher beschreiben, werde es aber nicht tun, da sich dann jede Antwort über den gesamten Artikel hinziehen könnte. Und niemand wird Sie in einem Vorstellungsgespräch um diese Detailliertheit bitten.
Wenn Sie möchten, hinterlasse ich Links für eine tiefergehende Untersuchung. Lass uns fliegen!

11. Benennen Sie alle Methoden der Object-Klasse

Die Object- Klasse verfügt über 11 Methoden:
  1. Class<?> getClass() – Klasse des aktuellen Objekts abrufen;

  2. int hashCode() – den Hash-Code des aktuellen Objekts abrufen;

  3. boolean equals(Object obj) – vergleiche das aktuelle Objekt mit einem anderen Objekt;

  4. Object clone() – eine Kopie des aktuellen Objekts erstellen und zurückgeben;

  5. String toString() – die String-Darstellung des Objekts abrufen;

  6. void notify() – weckt einen Thread, der auf dem Monitor dieses Objekts wartet (die Auswahl des Threads ist zufällig);

  7. void notifyAll() – alle Threads wecken, die auf dem Monitor dieses Objekts warten;

  8. void wait() – den aktuellen Thread auf dem aktuellen Monitor warten lassen (den aktuellen Thread einfrieren), bis ein notify- oder notifyAll-Aufruf den Thread aufweckt (funktioniert nur in einem synchronisierten Block);

  9. void wait(long timeout) – lässt den aktuellen Thread auf dem aktuellen Monitor (auf dem aktuellen synchronisierten Block) warten, jedoch mit einem Timeout für das Verlassen des Wartezustands (oder noch einmal, bis ein notify- oder notifyAll-Aufruf den Thread aufweckt);

  10. void wait(long timeout, int nanos) – diese Methode ähnelt der vorherigen Methode, jedoch mit einem präziseren Timeout;

  11. void finalize() – diese Methode wird (endgültig) aufgerufen, bevor das Objekt vom Garbage Collector entfernt wird. Es wird verwendet, um erworbene Ressourcen zu bereinigen.

Um die Methoden hashCode , equal , clone , toString und finalize korrekt zu verwenden, müssen sie entsprechend den Besonderheiten der aktuellen Aufgabe überschrieben werden.

12. Was ist der Unterschied zwischen try-with-resources und try-catch-finally beim Arbeiten mit Ressourcen?

Normalerweise wird bei der Verwendung von try-catch-finally der letzte Block zum Schließen von Ressourcen verwendet. Java 7 führt die neue try-with-resources- Anweisung ein. Es ist analog zu try-catch-finally, um Ressourcen freizugeben, aber kompakter und lesbarer. Erinnern wir uns daran, wie try-catch-finally aussieht:
String text = "some text......";
BufferedWriter bufferedWriter = null;
try {
   bufferedWriter = new BufferedWriter(new FileWriter("someFileName"));
   bufferedWriter.write(text);
} catch (IOException e) {
   e.printStackTrace();
} finally {
   try {
       bufferedWriter.close();
   } catch (IOException e) {
       e.printStackTrace();
   }
}
Schreiben wir nun diesen Code um, verwenden jedoch „try-with-resources“ :
String text = "some text......";
try(BufferedWriter bufferedWriter =new BufferedWriter(new FileWriter("someFileName"))) {
   bufferedWriter.write(text);
} catch (IOException e) {
   e.printStackTrace();
}
Das ist doch irgendwie einfacher, finden Sie nicht? Neben dem einfacheren Code sind noch einige weitere Punkte zu beachten:
  1. In try-with-resources müssen die in Klammern deklarierten Ressourcen (Ressourcen, die geschlossen werden) die AutoCloseable- Schnittstelle und ihre einzige close()- Methode implementieren .

    Die close-Methode wird in einem impliziten „finally“ -Block ausgeführt . Wie würde das Programm sonst genau herausfinden, wie die Ressource geschlossen werden soll?

    Aber Sie werden wahrscheinlich selten Ihre eigenen Implementierungen von Ressourcen und deren Abschlussmethode schreiben.

  2. Blöcke werden in dieser Reihenfolge ausgeführt:

    1. Der Try- Block.
    2. Der implizite „ final“ -Block.
    3. Der Catch- Block, der Ausnahmen abfängt, die in den vorherigen Schritten aufgetreten sind.
    4. Der explizite „final“ -Block.

    In der Regel unterbrechen die weiter unten in der Liste ausgelösten Ausnahmen die weiter oben ausgelösten Ausnahmen.

Stellen Sie sich vor, Sie verwenden einen Try-Catch-finally und erhalten eine Ausnahme im Try- Block. Dann beginnt sofort die Ausführung des angegebenen Catch-Blocks, in den wir eine weitere Ausnahme geschrieben haben (z. B. mit einer Meldung, die den Fehler genauer beschreibt), und Sie möchten, dass die Methode diese Ausnahme nach oben wirft . Dann wird der „finally“ -Block ausgeführt und auch darin eine Ausnahme ausgelöst. Aber dieses Mal ein anderes. Welche dieser beiden Ausnahmen wird diese Methode letztendlich auslösen? Die vom „finally “-Block ausgelöste Ausnahme! Aber jetzt sind wir bei einem anderen Punkt zum Thema try-with-resources angelangt . Betrachten wir, wie sich try-with-resources in derselben Situation verhält. Wir bekommen eine Ausnahme im try- Block, wenn wir versuchen, Ressourcen in der close()- Methode, also im impliziten Finally- Block, zu schließen. Welche dieser Ausnahmen wird der Catch-Block abfangen ? Der vom Try- Block geworfene! Die Ausnahme vom impliziten „ final“ -Block (von der lose()- Methode) wird ignoriert. Dieses Ignorieren von Ausnahmen wird auch Ausnahmeunterdrückung genannt.

13. Was sind bitweise Operationen?

Bitweise Operationen sind Operationen an Bitfolgen. Dazu gehören logische Operationen und bitweise Verschiebungen. Logische Operatoren:
  • bitweises UND – Vergleicht Bitwerte. Jedes auf 0 (falsch) gesetzte Bit setzt das entsprechende Bit im Ergebnis auf 0. Das heißt, wenn ein Bit in beiden verglichenen Werten 1 (wahr) ist, ist das resultierende Bit ebenfalls 1.

    Wird als AND oder & bezeichnet

    Beispiel: 10111101 & 01100111 = 00100101

  • bitweises ODER – Diese Operation ist das Gegenteil der vorherigen. Jedes auf 1 gesetzte Bit setzt das entsprechende Bit im Ergebnis auf 1. Wenn dementsprechend das Bit in beiden verglichenen Werten 0 ist, ist auch das resultierende Bit 0.

    Wird als OR oder | bezeichnet

    Beispiel: 10100101 | 01100011 = 11100111

  • bitweises NICHT – Dieser Operator wird auf einen einzelnen Wert angewendet. Es dreht (invertiert) die Bits. Das heißt, die Bits, die 1 waren, werden zu 0; und diejenigen, die 0 waren, werden 1.

    Wird als NOT oder ~ bezeichnet

    Beispiel: ~10100101 = 01011010

  • Bitweises Exklusiv- ODER – Vergleicht Bitwerte. Wenn beide Bits 1 sind, ist das resultierende Bit 0. Wenn beide Bits 0 sind, ist das resultierende Bit 0. Mit anderen Worten: Damit das resultierende Bit 1 ist, muss nur eines der Bits 1 sein, und das andere Bit muss 0 sein.

    Wird als XOR oder ^ bezeichnet

    Beispiel: 10100101 ^ 01100011 = 11000110

Bitweise Verschiebungen ( >> und << ) verschieben die Bits des Operanden in die angegebene Richtung um die angegebene Anzahl von Stellen. Frei gewordene Positionen werden mit Nullen aufgefüllt. Zum Beispiel:
  1. 01100011 >> 4 = 00000110
  2. 01100011 << 3 = 00011000
Die Ausnahme besteht, wenn Sie eine negative Zahl nach rechts verschieben. Wie Sie sich erinnern, gibt das erste Bit einer vorzeichenbehafteten Zahl das Vorzeichen an. Wenn dieses Bit 1 ist, ist die Zahl negativ. Wenn Sie eine negative Zahl verschieben, werden die frei gewordenen Stellen nicht mit Nullen, sondern mit Einsen aufgefüllt, da das Vorzeichenbit erhalten bleiben muss. Zum Beispiel: 10100010 >> 2 = 11101000 Allerdings verfügt Java über einen zusätzlichen vorzeichenlosen Rechtsverschiebungsoperator (>>>). Dieser Operator ist analog zu >>, aber beim Verschieben werden frei gewordene Positionen mit 0 aufgefüllt, unabhängig davon, ob der Operand eine negative oder eine positive Zahl ist. Zum Beispiel: 10100010 >>> 2 = 00101000 Lesen Sie hier mehr über bitweise Operationen . Erkundung der Fragen und Antworten aus einem Vorstellungsgespräch für eine Stelle als Java-Entwickler.  Teil 2 - 2Sie können die Methode hash() in HashMaps als Beispiel für bitweise Verschiebungen in Java nehmen. Mit dieser Methode wird der spezielle interne Hashcode des Schlüssels ermittelt: Mit Erkundung der Fragen und Antworten aus einem Vorstellungsgespräch für eine Stelle als Java-Entwickler.  Teil 2 - 3dieser Methode können Sie die Daten in einer HashMap gleichmäßig verteilen, um die Anzahl der Kollisionen zu minimieren.

14. Welche unveränderlichen Standardobjekte gibt es in Java?

Ein Objekt ist unveränderlich , wenn es keine Änderung seiner ursprünglichen Werte zulässt. Es kann Methoden geben, die neue Objekte desselben Typs mit unterschiedlichen Werten zurückgeben. Zu den standardmäßigen unveränderlichen Objekten gehören:
  • Zweifellos ist String der bekannteste unveränderliche Typ von Java.
  • Instanzen der Wrapper-Klassen, die Standardtypen umschließen: Boolean, Character, Byte, Short, Integer, Long, Double, Float;
  • BigInteger- und BigDecimal-Objekte, die normalerweise für besonders große Zahlen verwendet werden;
  • StackTraceElement-Objekte, die einen Stack-Trace bilden (z. B. den Stack-Trace einer Ausnahme);
  • ein Objekt der File-Klasse – es kann Dateien ändern, aber gleichzeitig bleibt das Objekt selbst unverändert;
  • UUIDs, die häufig zur eindeutigen Identifizierung von Elementen verwendet werden;
  • alle Objekte von Klassen im java.time-Paket;
  • Gebietsschemaobjekte, die zur Identifizierung einer geografischen, politischen oder kulturellen Region verwendet werden.

15. Welche Vorteile haben unveränderliche Objekte gegenüber gewöhnlichen Objekten?

  1. Unveränderliche Objekte können sicher in einer Multithread-Umgebung verwendet werden . Sie sorgen dafür, dass Sie sich keine Sorgen über Datenverlust aufgrund von Rennbedingungen machen müssen. Dies ist anders als bei der Arbeit mit gewöhnlichen Objekten. In diesem Fall müssen Sie über gute Mechanismen nachdenken und sie entwickeln, wenn Sie das Objekt in einer parallelen Umgebung verwenden.

  2. Unveränderliche Objekte eignen sich gut als Schlüssel in einer Karte. Wenn Sie ein veränderliches Objekt als HashMap-Schlüssel verwenden und sich dann der Status des Objekts ändert, könnte die Datenstruktur durcheinander geraten: Das Objekt ist immer noch vorhanden, aber wenn Sie containsKey() verwenden, können Sie es möglicherweise nicht finden.

  3. Unveränderliche Objekte eignen sich hervorragend zum Speichern unveränderlicher (konstanter) Daten, die niemals geändert werden sollten, während das Programm ausgeführt wird.

  4. Ein weiterer Vorteil ist die Fehleratomarität. Wenn ein unveränderliches Objekt eine Ausnahme auslöst, verbleibt es nicht in einem unerwünschten (kaputten) Zustand.

  5. Diese Klassen sind einfach zu testen.

  6. Sie benötigen keine zusätzlichen Mechanismen wie einen Kopierkonstruktor oder die Implementierung des Objektklonens.

Fragen zu OOP

16. Was sind die Vorteile von OOP im Allgemeinen und im Vergleich zur prozeduralen Programmierung?

Okay, Vorteile von OOP:
  1. Komplexe Anwendungen lassen sich mit OOP einfacher schreiben als mit prozeduraler Programmierung, da alles in kleine Module – Objekte, die miteinander interagieren – zerlegt wird und sich die Programmierung dadurch auf Beziehungen zwischen Objekten reduziert.

  2. Mit OOP geschriebene Anwendungen lassen sich viel einfacher ändern (wenn die Designprinzipien ordnungsgemäß beachtet werden).

  3. Da sowohl die Daten als auch die Datenoperationen eine einzige Einheit bilden, sind sie nicht in der gesamten Anwendung verteilt (was bei der prozeduralen Programmierung häufig der Fall ist).

  4. Das Prinzip der Kapselung schützt die kritischsten Daten vor dem Benutzer.

  5. Derselbe Code kann mit unterschiedlichen Daten wiederverwendet werden, da Sie mit Klassen viele Objekte mit jeweils eigenen Werten erstellen können.

  6. Durch Vererbung und Polymorphismus können Sie außerdem vorhandenen Code wiederverwenden und erweitern (anstatt ähnliche Funktionen zu duplizieren).

  7. Eine Antragsverlängerung ist einfacher als mit einem verfahrensrechtlichen Vorgehen.

  8. Der OOP-Ansatz ermöglicht die Abstrahierung von Implementierungsdetails.

17. Sagen Sie uns, welche Nachteile OOP hat

Leider gibt es sie auch:
  1. OOP erfordert viel theoretisches Wissen, das beherrscht werden muss, bevor man etwas schreiben kann.

  2. OOP-Ideen sind nicht so einfach zu verstehen und in der Praxis anzuwenden (man muss im Herzen ein kleiner Philosoph sein).

  3. OOP reduziert die Leistung eines Programms aufgrund der erhöhten Komplexität des Systems geringfügig.

  4. Der OOP-Ansatz erfordert mehr Speicher, da alles aus Klassen, Schnittstellen und Methoden besteht, die viel mehr Speicher beanspruchen als gewöhnliche Variablen.

  5. Der Zeitaufwand für die Erstanalyse ist größer als für eine prozessuale Vorgehensweise.

18. Was ist statischer Polymorphismus im Vergleich zu dynamischem Polymorphismus?

Durch Polymorphismus können sich Objekte derselben Klasse oder Schnittstelle unterschiedlich verhalten. Es gibt zwei Arten von Polymorphismus, die auch als frühe und späte Bindung bezeichnet werden. Statischer Polymorphismus oder frühe Bindung:
  • Tritt zur Kompilierzeit auf (früh im Lebenszyklus des Programms);
  • entscheidet, welche Methode zur Kompilierzeit ausgeführt werden soll;
  • Methodenüberladung ist ein Beispiel für statischen Polymorphismus;
  • Die frühe Bindung umfasst private, statische und endgültige Methoden.
  • Vererbung ist an der frühen Bindung nicht beteiligt;
  • Beim statischen Polymorphismus handelt es sich nicht um bestimmte Objekte, sondern um Informationen über den Klassentyp, der links neben einem Variablennamen angezeigt wird.
Dynamischer Polymorphismus oder späte Bindung:
  • tritt zur Laufzeit auf (während das Programm ausgeführt wird);
  • Der dynamische Polymorphismus entscheidet darüber, welche spezifische Implementierung eine Methode zur Laufzeit haben wird.
  • Das Überschreiben von Methoden ist ein Beispiel für dynamischen Polymorphismus.
  • Beim späten Binden wird ein bestimmtes Objekt, eine Referenz seines Typs oder seine Oberklasse zugewiesen.
  • Vererbung ist mit dynamischem Polymorphismus verbunden.

19. Geben Sie eine Definition des Abstraktionsprinzips in OOP an

In OOP ist Abstraktion eine Möglichkeit, eine Reihe bedeutungsvoller Merkmale eines Objekts zu isolieren und gleichzeitig unbedeutende Details auszuschließen. Das heißt, wenn Sie ein Programm mit einem OOP-Ansatz entwerfen, konzentrieren Sie sich auf allgemeine Modelle, ohne auf die Details ihrer Implementierung einzugehen. In Java wird die Abstraktion über Schnittstellen realisiert . Sie haben zum Beispiel ein Auto und das wird eine Schnittstelle sein. Und die verschiedenen Interaktionen damit – zum Beispiel das Starten des Motors, das Schalten der Gänge – sind Funktionen, die wir nutzen, ohne uns mit den Implementierungsdetails zu befassen. Tatsächlich denkt man beim Fahren nicht genau darüber nach, wie das Getriebe seinen Zweck erfüllt, wie der Schlüssel den Motor startet oder wie genau das Lenkrad die Räder dreht. Und wenn Sie die Implementierung einiger Funktionen (z. B. der Engine) ersetzen, bemerken Sie dies möglicherweise nicht einmal. Für Sie spielt es keine Rolle: Sie vertiefen sich nicht in die Implementierungsdetails. Für Sie zählt, dass die Aktion ausgeführt wird. Im Wesentlichen handelt es sich dabei um die Abstrahierung von Implementierungsdetails. An dieser Stelle machen wir heute Schluss: Fortsetzung folgt!
Kommentare
  • Beliebt
  • Neu
  • Alt
Du musst angemeldet sein, um einen Kommentar schreiben zu können
Auf dieser Seite gibt es noch keine Kommentare