Du verwendest einen veralteten Browser. Es ist möglich, dass diese oder andere Websites nicht korrekt angezeigt werden. Du solltest ein Upgrade durchführen oder ein alternativer Browser verwenden.
Das Prog soll einfach eine Bin-Datei "hex-cd" in eine neue "hex-out" kopieren -
(nur um die Funktion der Sprungmarke hinzubekommen, und gerade da hängt's):
Code:
// Imports
import java.io.*;
class T
{ public static void main ( String[] args ) throws IOException
{
RandomAccessFile inStr = new RandomAccessFile("hex-cd","r"); // wird nur zum lesen geöffnet
File file_02 = new File("hex-out"); // für Dateizugriff auf hex-out
file_02.delete(); // Löscht vorsichtshalber eine etwa bestehende Datei "hex-out"
// diese sollte nicht durch ein anderes Program geöffnet sein
RandomAccessFile outStr = new RandomAccessFile("hex-out","rw"); // und legt sie neu an (leer)
File file_01 = new File("hex-cd"); // für Dateizugriff auf hex-cd
// Variablendeklaration:
byte b000 = 0x00;
// Prog. selbst:
int zaehler = 1;
while ( zaehler < 2 ) // absichtliche Endlosschleife
{
b000 = inStr.readByte();
if (b000 < 0xFF) { outStr.writeByte(b000); }
if (b000 == 0xFF) { outStr.writeByte(b000);
continue sprungmarke; }
}
sprungmarke:
// planmäßiges Ende:
outStr.close(); // Datei "hex-out" schließen
inStr.close(); // Datei "hex-cd" schließen
}
}
Man kann Sprungmarken nur auf Schleifenanfänge legen und diese Marken auch nur aus diesen Schleifen heraus benutzen, was impliziert, dass die Sprungmarke bereits bekannt ist, bevor sie einmal benutzt wurde (Letzteres erklärt die Fehlermeldung).
Heist das, ich komme so aus dem if-Block nie raus und verlasse auch noch die while-Schleife?
Oder reicht es, wenn ich an das Ende einfach ein break anhänge?
Code:
if (b000 == 0xFF) { outStr.writeByte(b000);
continue sprungmarke; }
break;
... was dann aber nur bei der letzten if-Anweisung funzt???
In meiner Test-Datei ist das das letzte Byte - in "Echt" muss ich da noch etwas mehr schreiben - daher auch die vielen if-Blöcke - es ist eine Art Verschlüsselung ... - genau genommen eine Art Pack-Algorithmus.
int zaehler = 1;
while ( zaehler < 2 ) // absichtliche Endlosschleife
{
if (b000 == 0xFF) break;
b000 = inStr.readByte();
outStr.writeByte(b000);
}
Interessannterweise wird es anstandslos compiliert - zur Laufzeit ergibt aber den Fehler:
Code:
Exception in thread "main" java.io.EOFException
at java.io.RandomAccessFile.readByte(Unknown Source)
at T.main(T.java:32)
- das auch wenn die Datei hex-cd am Ende ZWEI Bytes "FF" hat - und EINS wird immer in die neue Datei kopiert, obwohl der break doch vorher steht.
Aber sonst funzt es wenigstens ...
Es gibt in der Ausgangs-Datei "Spezielle Bytes" die eine Pack-Methode anzeigen (daher brauche ich eigentlich einen Sprung aus einem if-Block in einer while-Schleife, heraus aus der while-Schleife, wobei ein "Spezielles Byte" mit Wert "FF" das Datei-Ende anzeigt -
(Ja für Profis geht es bestimmt ganz leicht - ich könnte die Datei-Größe abfragen und an die while-Schleife übergeben - ist mir gerade so eingefallen - aber allein das zu einem Programm zu bringen, was dann noch 100%ig läuft will ich mir ersparen, weil Anfänger ...)
Bitte beachte den Hinweis, der eigentlich unübersehbar rot angebracht ist.
Das mit der Endlosschleife habe ich nicht grundlos anders geschrieben. Zunächst einmal ist dein [c]zaehler < 2[/c]-Konstrukt total umständlich und verschlechtert die Lesbarkeit. Hinzu kommt (und das ist wichtiger), dass ich nicht readByte(), sondern read() verwende. Bitte lies dir die API-Dokumentation dazu durch, dann verstehst du auch, was es mit meinem [c]>= 0[/c] auf sich hat und warum du dir das mit 0xFF sparen kannst.
In deinem Versuch, dass Dateiende an 0xFF zu erkennen, findet sich ein schwerwiegender logischer Fehler: Im ersten Schritt kann dein [c]if[/c] nichts Sinnvolles überprüfen (schon das allein ist ein Fehler!), und nach dem Einlesen mittels [c]readByte[/c] (was du aus oben angedeuteten Gründen nicht tun solltest) wird das soeben eingelesene Byte unkontrolliert wieder rausgeschrieben; deswegen auch das 0xFF mehr am Ende.
Du solltest dein Konzept noch einmal überdenken und vor allem dir die API-Dokumentation zu Gemüte führen. Ich denke übrigens, FileInputStream und FileOutputStream sind für deine Aufgaben besser geeignet, zumal man dort Zugriffe leicht puffern kann.
solche Marker-Bytes machen bei Dateien keinen Sinn ... eine Datei hat immer einen Anfang und ein Ende ... beides lässt sich über die API finden
anders ist es im Netzwerk / COM-Port / $WHATEVER ... da gibt es keinen Anfang und kein Ende (mehr oder weniger schon - egal) ... und hier kannst Du ein Marker-Byte zur Synchonisation mit dem Stream verwenden - wird eigentlich in allen API's gemacht
Hatte ich am Anfang, ist aber für Anfänger ungeeignet, da ich dann ein Array erstellen muss und damit arbeiten, erschien mir schwieriger, es gibt einiges mehr zu beachten - lief nie ... Der Dateizugriff mit RandomAccessFile sind 2 Zeilen und vorher mit BufferedInputStream waren es 4.
Wenn du dir ganz viele Probleme mit Vorzeichen einhandeln willst, kannst du gerne byte verwenden. Möchtest du es bequem haben: benutze int, aber halt nur die letzten 8 bits.