Eigener FilterReader

lissy

Mitglied
Hallo allerseits ;-)

Es geht darum, einen Text aus einer Textdatei zu lesen, zu filtern und anschließend auszugeben.
Soweit so gut. Syntaktisch funktioniert mein Code, allerdings kommt nicht das Gewünschte bei raus.

Generell sieht es so aus:
in der Main:
Java:
FileReader fr = new FileReader("text.txt");
FilterA filterA = new FilterA(fr);
while(filterA.read() != -1) System.out.print((char) filterA.read());
filterA.close();

und der Filter sieht so aus:
Java:
public FilterA(Reader in) {
        super(in);
    }

    @Override
    public int read() throws IOException {
        
        if (Character.toString((char) in.read()).matches("[^a-zA-Z0-9]")) {
             return ' ';
        } else {
             return Character.toLowerCase((char) in.read());
        }
    }

Läuft die Schleifen oben durch, kommt allerdings nicht wie gewünscht ein Leerzeichen für Sonderzeichen und Kleinbuchstaben raus, sondern irgendwas andres teilweise kryptischen, was ich mir nicht erklären kann.

Könnte mir jemand eine Tipp geben, woran es liegen kann?
UTF8 ist übrigens eingestellt beim Kompilieren.

1000 Dank :toll:
 

SilverClaw

Aktives Mitglied
Ich verstehe ja nicht ganz, was du da vor hast, aber es hinkt schonmal daran, dass in.read() immer eins weiter springt und wenn du es in deiner Bedingung aufrufst und danach nochmal in eine rAusgabe, dann sind das eben komplett verschiedene Zeichen. Speichere es zwischen, wenn es so sein muss.
Andererseits ist dein Weg wohl auch der ineffekticste, um Buchstaben aus einer Datei zu bekommen.
Speichere doch besser deine Datei (die du mit BufferedReader viel schneller einlesen kannst) zwischen (oder Teile davon, wenn sie sehr groß ist) und lass mit deinem regulären Ausdruck dann einen matcher drüber laufen.
 

lissy

Mitglied
Hey ;)
danke schon mal für die Antwort.
Dass in.read() jedes Mal einen weiter springt, wusste ich noch nicht.

Kurz noch zum Ziel des Ganzen:
Alle Sonderzeichen sollen in Leerzeichen umgewandelt werden. Alle anderen Buchstaben sollen in Kleinbuchstaben umgewandelt werden.

Ich habe den Code jetzt nach deiner Empfehlung hin modifiziert.
Java:
FileReader fr = new FileReader("test.txt");
BufferedReader br = new BufferedReader(fr);
FilterA filterA = new FilterA(br);
while(filterA.read() != -1) System.out.print((char) filterA.read());
filterA.close();

und den Filter:
Java:
public FilterA(Reader in) {
        super(in);
    }

    @Override
    public int read() throws IOException {
        int c = in.read();
        
        if (Character.toString((char) c).matches("[^a-zA-Z0-9]")) {
             return ' ';
        } else {
             return Character.toLowerCase((char) c);
        }
    }

Leider ändert das nicht viel. Das Einlesen bzw. Ausgeben dauert auch enorm lange.
 
Zuletzt bearbeitet:

SilverClaw

Aktives Mitglied
Habe selbst mal kurz rumgebastelt, finde, dass es damit recht flott geht, aber war nun auch zu faul, mit eine wirklich große Datei zum testen zurecht zu legen.
Wenn ich es so starte, ist das Ergebnis eigentlich sofort da.
Je nachdem, wie du mit Zeilenumbrüchen umgehen willst, musst du es noch anpassen.

Java:
		StringBuilder builder = new StringBuilder(1024);
		BufferedInputStream bis = null;
		BufferedReader reader;
		try {
			reader = new BufferedReader(
					new FileReader(System.getProperty("user.home") + "\\Desktop\\conway.txt"));
			while(reader.ready()) {
			builder.append(reader.readLine() + "\n");
		}
		} catch (FileNotFoundException e) {
			// TODO Auto-generated catch block
			e.printStackTrace();
		} catch (IOException e) {
			// TODO Auto-generated catch block
			e.printStackTrace();
		}
		System.out.println(builder.toString().toLowerCase().replaceAll("[^A-z0-9]", " "));
 

lissy

Mitglied
Hi. Danke nochmals!

Umbrüche brauche ich keine mehr nach dem filterA.

Der BufferedInputStream wird bei dir nicht verwendet oder?
Eventuell hätte es daran liegen können.

Ansonsten muss ich mal schauen, ob ich nicht doch besser die reader(char[] cbuf, int offset, int len) verwende, um effektiver zu sein.
 

SilverClaw

Aktives Mitglied
Mit BufferedInputStream ginge es auch aber nextLine(); braucht halt weniger append-Befehle und war in dem fall bequemer. :D

habe überlegt, dass builder.toString().replaceAll("[^A-z0-9\n]", " ").toLowerCase() eventuell noch minimal schneller ist, weil er dann weniger Buchstaben "umwandeln" muss. Es köntnne aber auch Messfehler sein ;)
 

lissy

Mitglied
In Ordnung. Der Unterschied spielt sich vermutlich im Nanosekundenbereich ab. :D
StringBuilder etc. kann ich in dem Filter nur leider nicht verwenden, weil man da ja lediglich einzelne Zeichen modifizieren kann.
:bahnhof:
 

SilverClaw

Aktives Mitglied
Anmerkung zu vorhin: ich glaube, der BufferedReader benutzt intern sowieso einen BufferedInputStream, aber nagel mich nciht darauf fest. :bahnhof:

In Ordnung. Der Unterschied spielt sich vermutlich im Nanosekundenbereich ab.

Möglich, aber ich verschwende ungerne Millisekunden (bei größeren Dateien), wenn es sich so einfach vermeiden lässt.
Ich verstehe aber dein Problem nicht. Ich dachte, es kommt raus, was du wolltest. Wofür solltest du die setCharAt()-Methoden rbauchen...oder meinst du die überhaupt? :autsch:
 

lissy

Mitglied
Ich verstehe aber dein Problem nicht. Ich dachte, es kommt raus, was du wolltest. Wofür solltest du die setCharAt()-Methoden rbauchen...oder meinst du die überhaupt? :autsch:

Nein, läuft noch nicht wie es soll.
Der Algorithmus macht z.B. noch aus einem H ein Leerzeichen, es soll aber ein h rauskommen.
Ich habe die Logik ein paar Mal manuell getestet und sie funktioniert wie gewollt.
Daraus schließe ich jetzt mal, dass immernoch das in.read() irgendwo dazwischenfunkt.

Der letzte Code, den ich gepostet haben, ist noch aktuell.
Bewirkt die Zuweisung
Java:
int c = in.read();
etwa auch ein Weiterspringen?

Dankeschön :)
 
Zuletzt bearbeitet:

SilverClaw

Aktives Mitglied
Welcher denn nun? Wenn ich in meine Datei H!XOOOO schreibe, kommt bei meiner Methode h xoooo
raus. Was du da machst, weiß ich ja nicht. :p

int c = in.read();

Bei jedem .read() wird das nächste Byte ausgelesen.

bei

Java:
int a = in.read();
int b = in.read();

wären a und b verschiedene Zahlen (sofern die Datei nicht shcon zu Ende ist und beide -1 ergeben...und natürlich, falls auch tatsächlich verschiedene Zeichen in der Datei stehen).

Um das in lesbare Zeichen umzuwandeln, reicht ein
Java:
char c = (char) a;
nicht aus.
Wenn a zum Beispiel 5 wäre und du auf UTF 8 gestellt hast, sollte dir das das 8. Zeichen deiner UTF-Tabelle ausgeben.
Java:
char c = (char) a + 'a';
dürfte helfen.

edit: bevor es wegen der Namen Verwirrung gibt. für char c = (char) h + 'a'
gilt das gleiche, es geht nur daum, dass das 'a' ja den Wert des ersten Kleinbuchstaben in der Code-Tabelle repräsentiert.
 
Zuletzt bearbeitet:

lissy

Mitglied
Ist ja merkwürdig ???:L

Also wie gesagt, das hier ist meine aktueller Code:
Java:
 FileReader fr = new FileReader("test.txt");
            BufferedReader br = new BufferedReader(fr);
            FilterA filterA = new FilterA(br);
            //FilterB filterB = new FilterB(filterA);
            //FilterC filterC = new FilterC(filterB);
            
            while(filterA.read() != -1) System.out.print((char) filterA.read());
            
            
            filterA.close();

und das der Filter:
Java:
import java.io.FilterReader;
import java.io.IOException;
import java.io.Reader;

public class FilterA extends FilterReader {

    public FilterA(Reader in) throws IOException {
        super(in);
    }

    @Override
    public int read() throws IOException {
        int c = in.read();
        if (Character.toString((char) c).matches("[^a-zA-Z0-9]")) {
            return ' ';
        } else {
            return Character.toLowerCase((char) c);
        }
    }
}

Und raus kommt nicht das Richtige :)
Ich habe die Befürchtung, dass sich alles noch um eine Stelle weiter verschiebt durch ein mögliches überflüssiges in.read(). Aber das einzige ist halt die Zuweisung zu
Code:
int c = in.read();
 

SilverClaw

Aktives Mitglied
Dir ist schon klar, dass du mit
Java:
while(filterA.read() != -1) System.out.print((char) filterA.read());
einmal für die Bedingung die read()-Methode aufrufst und dann wahrscheinlich nur jedes zweite Ergebnis ausgeben lässt?

Außerdem ist
Java:
(Character.toString((char) c).matches("[^a-zA-Z0-9]"))
weiterhin eine recht ineffektive Methode, weil du ja für jedes Zeichen erst von einem int in zu einem char und dann zu einem String convertierst und nebenbei mit matches() noch ein boolean hast...lass das einfach.
Trenne lieber das Einlesen der Daten und das Nachbearbeiten komplett, dann geht auch weniger schief, falls die Datei nicht gefundne wird oder kaputt ist. Im jetzigen Zustand ist dein FilteredReader einfach nur unnötig performancefressend und, wie du ja sehen kannst, schwer verständlich. ;)
 

lissy

Mitglied
Ha, tatsächlich!
Statt der while-Schleife habe ich jetzt eine for gemacht und es scheint zu klappen.

Wegen dem Umwandeln muss ich mir noch etwas besseres überlegen.

Vielen Danke auf jeden Fall!:applaus:
 
Ähnliche Java Themen
  Titel Forum Antworten Datum
H String verschlüsseln - eigener Algorithmus Java Basics - Anfänger-Themen 104
D importieren eigener Klassen Java Basics - Anfänger-Themen 12
W Dez-->Binär mit eigener bit Anzahl Erkennung. Java Basics - Anfänger-Themen 3
N ArrayList in eigener Klasse erzeugen mit Zugriff Java Basics - Anfänger-Themen 7
B Eigener Validierungseditor? Java Basics - Anfänger-Themen 3
W Eigener Iterator soll mehrdimensionales Array durchlaufen Java Basics - Anfänger-Themen 4
Bluedaishi Jar mit eigener JRE Java Basics - Anfänger-Themen 7
I equals (Override) mit eigener Exception (keine Runtime-Exception) Java Basics - Anfänger-Themen 9
J Threads Problem mit eigener ArrayList Java Basics - Anfänger-Themen 2
E MCLauncher eigener Client workt nicht? Java Basics - Anfänger-Themen 4
A Input/Output Datenströme schließen in eigener Methode Java Basics - Anfänger-Themen 5
J Interface ActionListener in eigener Klasse Java Basics - Anfänger-Themen 27
F Get/Post als eigener Thread mit Rückgabe Java Basics - Anfänger-Themen 5
M Messandwendung nach Zeit und eigener Eingabe Java Basics - Anfänger-Themen 4
N Schlüsselworte Bubble Sort nach eigener Ordnung Java Basics - Anfänger-Themen 8
E Compare-Funktion bei eigener Klasse Java Basics - Anfänger-Themen 4
Q ArrayList mit eigener Klasse in Java sotieren Java Basics - Anfänger-Themen 2
N BierSpiel von "Kopf bis Fuss" eigener Code...kleine Problemstellung. Java Basics - Anfänger-Themen 11
C OOP Erstellen eigener Objekte die es schon gibt "schlau"? Java Basics - Anfänger-Themen 3
V Arrays aus eigener Klasse erstellt, zuweisung aber spuckt Fehler in verbindung mit main Methode aus. Java Basics - Anfänger-Themen 3
E Mein eigener Listener (Hilfe gesucht) Java Basics - Anfänger-Themen 2
M import von eigener Klasse Java Basics - Anfänger-Themen 12
P ArrayList aus eigener Klasse "überschreibt" Werte nicht Java Basics - Anfänger-Themen 4
M xPos und yPos eigener Klassen geben lassen Java Basics - Anfänger-Themen 3
H Exit Befehl in eigener Konsole Java Basics - Anfänger-Themen 9
S Eigener InputStream, Hilfe bei read-Methode Java Basics - Anfänger-Themen 6
S Überladener Konstruktor und aufruf aus eigener Klasse Java Basics - Anfänger-Themen 2
D Klassen Problem mit Eigener Array-Klasse Java Basics - Anfänger-Themen 10
S [JUnit] eigener Testsuite Runner + Ausgabe Java Basics - Anfänger-Themen 6
G Eigener Autoboxing Datentyp Java Basics - Anfänger-Themen 3
M Eigener InputStream will nicht mit BufferedReader Java Basics - Anfänger-Themen 3
B Datentypen Probleme mit eigenem Get() bei eigener HashMap Java Basics - Anfänger-Themen 6
B OOP Eigener Event-Listener erstellen Java Basics - Anfänger-Themen 4
G Datentypen "Liste" eigener Objekte durchsuchen Java Basics - Anfänger-Themen 6
S mit eigener Klasse JTextField ändern Java Basics - Anfänger-Themen 3
N Vektor mit eigener Datenstruktur sortieren Java Basics - Anfänger-Themen 20
I Datentypen Eigener DatenTyp Java Basics - Anfänger-Themen 2
B Ordner öffnen (eigener Dateibrowser) Java Basics - Anfänger-Themen 8
B Eigener Webserver + Eigener Webbrowser Java Basics - Anfänger-Themen 7
I eigener "Abstandshalter" vs. LayoutManager Java Basics - Anfänger-Themen 6
X eigener Mergesort auf generischen Typen mit Comparator Java Basics - Anfänger-Themen 6
K Sinn eigener Exceptions Java Basics - Anfänger-Themen 11
D Container mit eigener Klasse Java Basics - Anfänger-Themen 5
B Verwenden eigener Object-Klassen Java Basics - Anfänger-Themen 9
H Eigener Button Java Basics - Anfänger-Themen 2
M Eigener Iterator für LinkedList Java Basics - Anfänger-Themen 20
I Java eigener MSN Messenger schreiben Java Basics - Anfänger-Themen 3
R Event in eigener Klasse implementieren ? Java Basics - Anfänger-Themen 8
G Fortlaufende Aktualisierung bei eigener Klasse Java Basics - Anfänger-Themen 2
G IOException Problem in eigener Klasse Java Basics - Anfänger-Themen 8
B Import Problem mit eigener Klasse. Java Basics - Anfänger-Themen 8
G Eigener Parser Java Basics - Anfänger-Themen 4
T Problem mit eigener Klasse Java Basics - Anfänger-Themen 7
A eigener Explorer via Java? Java Basics - Anfänger-Themen 9
D Thread und Process Kommunikation bei eigener Console Java Basics - Anfänger-Themen 2
T Öffnen externer Datei als eigener Prozess Java Basics - Anfänger-Themen 8
G Datei aus eigener JAR-Datei verwende Java Basics - Anfänger-Themen 2
N Porblem mit dem Importieren eigener Pakete Java Basics - Anfänger-Themen 4
T ActionListener in eigener Klasse Java Basics - Anfänger-Themen 10
T ActionListener in eigener Klasse Java Basics - Anfänger-Themen 5
L ActionListener in eigener Klasse Java Basics - Anfänger-Themen 3
T Erstellen eigener packages Java Basics - Anfänger-Themen 6
G JMenuBar in eigener Klasse erstellen Java Basics - Anfänger-Themen 3
A Eigener Datentyp? Java Basics - Anfänger-Themen 39
F Eigener IP-Paket-Header Java Basics - Anfänger-Themen 15

Ähnliche Java Themen

Neue Themen


Oben