CodeGym /Java-Blog /Random-DE /Lesen von der Tastatur: „Leser“
Autor
Aditi Nawghare
Software Engineer at Siemens

Lesen von der Tastatur: „Leser“

Veröffentlicht in der Gruppe Random-DE
Hallo! In den Lektionen und Aufgaben in Level 3 haben Sie gelernt, wie Sie Dinge auf der Konsole anzeigen und in die andere Richtung Daten von der Tastatur lesen.
Lesen von der Tastatur: „Leser“ – 1
Sie haben sogar gelernt, das folgende komplexe Konstrukt zu verwenden, um dies zu erreichen:

BufferedReader reader = new BufferedReader(new InputStreamReader(System.in));
Aber es gibt eine Frage, die wir noch nicht beantwortet haben.

Wie in aller Welt funktioniert das?

In der Realität sind Programme selten völlig unabhängig. Sie kommunizieren mit anderen Programmen, Systemen, dem Internet usw. Mit „kommunizieren“ meinen wir hauptsächlich „Daten austauschen“. Das heißt, sie empfangen einige externe Daten und senden auch interne Programmdaten irgendwohin. Beispiele für Programme, die Daten austauschen, gibt es im Alltag zuhauf. Auf vielen Websites können Sie sich beispielsweise mit Ihrem Facebook- oder Twitter-Konto anmelden, anstatt sich zu registrieren. In diesem Fall tauschen zwei Programme (z. B. Twitter und die Website, auf der Sie sich anmelden) die erforderlichen Daten aus. Das Endergebnis ist, dass Sie erfolgreich angemeldet sind. Das Wort „Stream“wird verwendet, um den Prozess des Datenaustauschs zu beschreiben. Woher kommt dieser Name? Nach Ihrer Erfahrung wird ein „Strom“ möglicherweise eher mit Flüssen als mit Programmierung in Verbindung gebracht. Das ist kein Zufall :) Ein Stream ist im Wesentlichen ein sich bewegendes Datenelement. Mit anderen Worten: Beim Programmieren fließt nicht Wasser, sondern Daten in Form von Bytes und Zeichen. Wir können Datenbits aus einem Datenstrom empfangen und diese dann verwenden. Auch hier verwenden wir die Wasser-Strömungs-Analogie: Sie können Wasser aus einem Fluss schöpfen, um Suppe zu kochen, ein Feuer zu löschen oder Ihre Blumen zu gießen. Mit Streams können Sie mit jeder Datenquelle arbeiten: ob das Internet, das Dateisystem Ihres Computers oder etwas anderes – es macht keinen Unterschied. Streams sind ein universelles Werkzeug. Sie ermöglichen einem Programm, Daten von überall zu empfangen (Eingabeströme) und sie überall hin zu senden (Ausgabeströme). Ihre Aufgabe ist dieselbe: Daten von einem Ort zu nehmen und an einen anderen zu senden. Es gibt zwei Arten von Streams:
  1. Eingabeströme werden zum Empfangen von Daten verwendet
  2. Ausgabestreams dienen zum Senden von Daten.
In Java werden diese Streams durch die Klassen InputStreamund implementiert OutputStream. Die Streams können jedoch auch anders kategorisiert werden. Neben Eingabe- und Ausgabeströmen spricht man auch von Byteströmen und Zeichenströmen . Die Bedeutung hier sollte klar genug sein: Ein Bytestream sendet Informationen als Satz von Bytes, während ein Zeichenstrom sie als Satz von Zeichen sendet. In dieser Lektion konzentrieren wir uns auf Eingabeströme. Ich werde am Ende der Lektion einen Link mit Informationen zu Ausgabestreams einfügen. Sie können es selbst lesen :) Schauen Sie sich nun diesen Code an:

BufferedReader reader = new BufferedReader(new InputStreamReader(System.in));
Fanden Sie diese Zeile beim Durchgehen der Lektionen nicht ziemlich einschüchternd? :) Das wird nicht mehr der Fall sein, wenn wir einmal erkundet haben, wie es funktioniert. Lasst uns die Dinge in Ordnung bringen. Wir fangen am Ende an. System.inist ein InputStreamObjekt, eine Instanz der Klasse, über die wir eingangs gesprochen haben. Es handelt sich um einen Eingabestream, der mit einem Systemeingabegerät (der Tastatur) verknüpft ist. Du kennst diesen Stream übrigens indirekt. Schließlich verwenden Sie häufig seinen „Kollegen“ – System.out! System.outist der Systemausgabestrom . Es wird verwendet, um Daten über Ihre bevorzugte Methode System.out.println(), die Sie ständig verwenden, an die Konsole auszugeben :) System.outist ein Stream zum Senden von Daten an die Konsole, währendSystem.indient zum Abrufen von Daten von der Tastatur. Es ist alles ganz einfach :) Darüber hinaus können wir ohne dieses riesige Konstrukt Daten von der Tastatur lesen. Wir können einfach schreiben: System.in.read();

public class Main {

   public static void main(String[] args) throws IOException {

       while (true) {
           int x = System.in.read();
           System.out.println(x);
       }
   }
}
Die InputStreamKlasse (denken Sie daran, System.ines ist ein InputStreamObjekt) verfügt über eine read()Methode, mit der Sie Daten lesen können. Es gibt ein Problem: Es werden Bytes gelesen , keine Zeichen . Es ist langweilig, nur englische Buchstaben zu verwenden, also versuchen wir, das chinesische Zeichen „魚“ über die Tastatur zu lesen (kopieren Sie einfach diesen Buchstaben von hier und fügen Sie ihn mit Strg + V auf dem PC oder Befehl + V auf dem Mac in die Konsole ein ) . Dieses Zeichen bedeutet übrigens „ein Fisch“. Konsolenausgabe: 233 173 154 10 Dieses Symbol und viele andere chinesische Zeichen belegen 3 Bytes im Speicher des Computers (im Gegensatz zu lateinischen Buchstaben, die nur 1 Byte belegen). In diesem Fall werden 4 Bytes aus dem Stream gelesen: Die ersten drei stellen das Zeichen „魚“ dar und das andere Byte stellt eine neue Zeile dar (Enter). Dementsprechend System.inist es in seiner ungeschönten Form für uns keine Option. Menschen (mit seltenen Ausnahmen!) wissen nicht, wie man Bytes liest. Aber die InputStreamReaderKlasse kommt zur Rettung! Mal sehen, was das für ein Tier ist.

BufferedReader bufferedReader = new BufferedReader(new InputStreamReader(System.in));
Wir übergeben System.inan das InputStreamReader -Objekt. Der Klassenname sagt es! Wir erstellen ein InputStreamReaderObjekt und übergeben ihm einen Eingabestream, aus dem es Daten liest. In diesem Fall...

new InputStreamReader(System.in)
...wir sagen es: „Sie lesen Daten aus dem Systemeingabestrom (von der Tastatur)“. Aber das ist nicht seine einzige Funktion! Der InputStreamReaderempfängt nicht nur Daten aus dem Stream. Außerdem werden Byteströme in Zeichenströme konvertiert . Mit anderen Worten: Sie müssen die Daten nicht mehr von „Einsen und Nullen“ in eine „für Menschen lesbare Sprache“ konvertieren. InputStreamreadertut alles für Sie. Natürlich InputStreamReaderist es nicht auf das Auslesen von Daten aus der Konsole beschränkt. Es kann auch Daten von anderen Orten lesen. Zum Beispiel aus einer Datei:

import java.io.FileInputStream;
import java.io.IOException;
import java.io.InputStreamReader;

public class Main {

   public static void main(String[] args) throws IOException {
       InputStreamReader inputStreamReader = new InputStreamReader(new FileInputStream("C:\\Users\\username\\Desktop\\testFile.txt"));
   }
}
Hier erstellen wir eine FileInputStream(eine Variante von InputStream), übergeben den Dateipfad und übergeben den Stream selbst an die InputStreamReader. Jetzt können Daten aus der Datei gelesen werden (natürlich nur, wenn tatsächlich eine Datei im Pfad vorhanden ist). Wir verwenden auch die Methode InputStreamReaderder Klasse, read()um Daten zu lesen (die Quelle der Daten spielt keine Rolle: die Konsole, eine Datei oder irgendwo anders). Was ist der Unterschied zwischen System.in.read()und InputStreamReader.read()?\ Versuchen wir noch einmal, das Zeichen „魚“ mit einem zu lesen InputStreamReader. Ich erinnere Sie daran, was tatsächlich gelesen wurde von System.in.read(): 233 173 154 10 Und wie funktioniert das InputStreamReaderGleiche?

public class Main {

   public static void main(String[] args) throws IOException {

       InputStreamReader reader = new InputStreamReader(System.in);
       while (true) {
           int x = reader.read();
           System.out.println(x);
       }
   }
}

Konsolenausgabe: 39770 10 Der Unterschied ist sofort ersichtlich. Das letzte Byte (das die neue Zeile darstellt) bleibt unverändert (die Zahl 10), aber das Zeichen „魚“ wurde in einen einzelnen Code „39770“ umgewandelt. Das bedeutet es, Zeichen zu lesen! Wenn Sie nicht glauben, dass 39770 den Buchstaben „魚“ darstellt, können Sie sich leicht selbst davon überzeugen :)
import java.io.IOException;

public class Main {

   public static void main(String[] args) throws IOException {

       char x = 39770;
       System.out.println(x);
   }
}

Konsolenausgabe: Aber wenn InputStreamReaderes so toll ist, warum brauchen wir es dann auch BufferedReader? InputStreamReaderweiß, wie man Daten liest und Bytes in Zeichen umwandelt. Was können wir mehr verlangen? Warum ein anderer Leser? :/ Die Antwort ist ganz einfach: für mehr Leistung und Komfort . Beginnen wir mit der Leistung. Beim BufferedReaderLesen von Daten wird ein spezieller Bereich namens Puffer verwendet, in dem die gelesenen Zeichen „gespeichert“ werden. Wenn diese Zeichen letztendlich im Programm benötigt werden, werden sie aus dem Puffer entnommen und nicht direkt aus der Datenquelle (Tastatur, Datei usw.). Das spart viele Ressourcen. Um zu verstehen, wie das funktioniert, stellen Sie sich einen Kurier in einem großen Unternehmen vor. Der Kurier sitzt in einem Büro und wartet darauf, dass jemand Pakete zur Zustellung bringt. Jedes Mal, wenn er ein neues Paket erhält, kann er sofort losfahren. Aber es könnte tagsüber viele Pakete geben. Er müsste viele Wege zwischen dem Büro und den Lieferadressen zurücklegen. Stattdessen stellt der Kurier einen Karton in sein Büro. Jeder legt sein Paket in die Kiste. Jetzt kann der Kurier in aller Ruhe das Paket entgegennehmen und von Adresse zu Adresse fahren. Das spart viel Zeit, da er nicht jedes Mal ins Büro zurückkehren muss. In diesem Beispiel ist die Box nur ein Puffer und das Büro eine Datenquelle. Für den Kurier ist es viel einfacher, bei Lieferungen Pakete aus einem einzigen Karton zu entnehmen, als jedes Mal ins Büro zurückzukehren. Er wird auch Benzin sparen. Ebenso ist es in einem Programm viel weniger ressourcenintensiv, Daten aus einem Puffer zu entnehmen, als jedes Mal auf die Datenquelle zu verweisen. Infolge,BufferedReader+ InputStreamReaderist schneller als InputStreamReaderallein . Wir haben an die Leistung gedacht. Wie sieht es mit der Bequemlichkeit aus? Der Hauptvorteil besteht darin, dass BufferedreaderDaten nicht nur zeichenweise gelesen werden können (obwohl dies mit der read()Methode möglich ist), sondern auch ganze Zeilen gleichzeitig! Dies geschieht mit der readLine()Methode;

public class Main {

   public static void main(String[] args) throws IOException {

       BufferedReader reader = new BufferedReader(new InputStreamReader(System.in));
       String s = reader.readLine();
       System.out.println("We read this line from the keyboard:");
       System.out.println(s);
   }
}

Konsolenausgabe: CodeGym ist die beste Website zum Erlernen von Java! Wir lesen diese Zeile von der Tastatur: CodeGym ist die beste Website zum Erlernen von Java! Dies ist besonders nützlich, wenn große Datenmengen gelesen werden. Das zeichenweise Lesen einer oder zweier Textzeilen ist immer noch möglich. Aber in „Krieg und Frieden“ einen Buchstaben nach dem anderen zu lesen, wäre etwas problematisch :)

Mehr Lektüre:

Kommentare
TO VIEW ALL COMMENTS OR TO MAKE A COMMENT,
GO TO FULL VERSION