2008-09-09 8 views
8

Die Sun Documentation for DataInput.skipBytes besagt, dass es "versucht, n Bytes von Daten aus dem Eingabestream zu überspringen, die übersprungenen Bytes zu verwerfen. Es kann jedoch einige kleinere Anzahl von Bytes überspringen, möglicherweise Null. Dies kann von einem beliebigen sein Anzahl der Bedingungen; Erreichen des Dateiendes, bevor n Bytes übersprungen wurden, ist nur eine Möglichkeit. "Wann kann DataInputStream.skipBytes (n) n Bytes nicht überspringen?

  1. Anders als das Ende der Datei erreicht, warum könnte skipBytes() nicht die richtige Anzahl von Bytes überspringen? (Die DataInputStream ich verwende entweder eine FileInputStream oder eine PipedInputStream werden Einwickeln.)

  2. Wenn ich auf jeden Fall überspringen wollen n Bytes und werfen einen EOFException wenn dies mir verursacht bis zum Ende der Datei zu gehen, sollte ich readFully() und das resultierende Byte-Array ignorieren? Oder gibt es einen besseren Weg?

Antwort

5

1) Es ist vielleicht nicht so viele Daten zu lesen (das andere Ende des Rohres nicht gesendet haben könnte, dass viele Daten noch) nicht, und die implementierende Klasse könnten nicht blockierenden (dh es wird nur zurückgeben, was es kann, anstatt auf genügend Daten zu warten, um die Anfrage zu erfüllen).

Ich weiß nicht, ob sich tatsächlich irgendwelche Implementierungen auf diese Weise verhalten, aber die Schnittstelle ist so konzipiert, dass sie dies zulässt.

Eine andere Option ist einfach, dass die Datei während des Lesevorgangs geschlossen wird.

2) Entweder readFully() (wird immer auf genügend Eingaben warten oder aber scheitern) oder skipBytes() in einer Schleife aufrufen. Ich denke, ersteres ist wahrscheinlich besser, es sei denn, das Array ist wirklich riesig.

1

Josh Bloch hat dies vor kurzem veröffentlicht. Es ist konsistent, dass InputStream.read nicht garantiert, so viele Bytes wie möglich zu lesen. Als API-Methode ist es jedoch völlig sinnlos. InputStream sollte wahrscheinlich auch readFully haben.

1

Es stellt sich heraus, dass ReadFully() mehr Performance Overhead hinzufügt, als ich bereit war zu ertragen.

Am Ende kompromittiert: Ich rufe skipBytes() einmal, und wenn das weniger als die richtige Anzahl von Bytes zurückgibt, rufe ich ReadFully() für die verbleibenden Bytes.

1

Ich bin heute auf dieses Problem gestoßen. Es wurde eine Netzwerkverbindung auf einer virtuellen Maschine abgelesen, also könnte es eine Reihe von Gründen dafür geben. Ich löste es, indem ich einfach den Eingabestrom zwang, Bytes zu überspringen, bis es die Anzahl der Bytes, die ich wollte, übersprungen hatte:

int byteOffsetX = someNumber; //n bytes to skip 
int nSkipped = 0; 

nSkipped = in.skipBytes(byteOffsetX); 
while (nSkipped < byteOffsetX) { 
    nSkipped = nSkipped + in.skipBytes(byteOffsetX - nSkipped); 
}