2010-11-24 4 views
6

Ich versuche herauszufinden, was ich hier falsch mache. Ich versuche, einen Binary Reader zu verwenden, um das Abrufen von ersten vier Bytes aus einem Stream in einen Int32-Wert zu erleichtern, der mir sagt, wie lange der Rest der Daten erwartet werden soll.C# BinaryReader.Read() ruft Junk zum Starten mit

static void Main(string[] args) 
{ 
    MemoryStream stream = new MemoryStream(); 

    BinaryWriter writer = new BinaryWriter(stream); 

    string s = "Imagine this is a very very long string."; 

    writer.Write(s.Length); 
    writer.Write(s); 
    writer.Flush(); 

    BinaryReader reader = new BinaryReader(stream); 
    reader.BaseStream.Seek(0, SeekOrigin.Begin); 

    char[] aChars = new char[reader.ReadInt32()]; 
    reader.Read(aChars, 0, aChars.Length); 
    Console.WriteLine(new string(aChars)); 
} 

sollte der Ausgang dem Eingang, aber ich dieses (Beachten Sie, dass die ersten Zeichen ändert sich von Saite zu Saite)

(Stellen Sie sich eine sehr sehr lange Zeichenfolge

Kann mir jemand erklären, was ich falsch mache? Idealerweise würde der zweite Lesevorgang so lange fortgesetzt, bis die Summe der gelesenen Bytes gleich dem Wert der ersten vier Bytes ist. Dieser Code ist nur eine Vereinfachung, um das Problem zu verdeutlichen. Die Position des Stromes scheint corr ect (4), aber es scheint fast so, als würde es bei 2 anfangen zu lesen.

+0

MSDN, Sie möchten es lesen. – jason

+0

Hehe, danke ... und ich war. Leider erwähnt der BinaryReader nicht, dass der Writer zusätzliche Daten für eine Zeichenkette als die Zeichenkette speichert;) – James

+0

'BinaryWriter.Write (Zeichenkette)': "Eine Zeichenkette mit Länge vorangestellt symbolisiert die 'Zeichenkettenlänge' durch Voranstellen von' string' ein einzelnes Byte oder Wort, das die Länge dieser 'string' enthält.Diese Methode schreibt zuerst die Länge der' string' als eine UTF-7-codierte, unsignierte Ganzzahl und schreibt dann so viele Zeichen in den Stream, dass '' verwendet wird BinaryWriter' Instanz aktuelle Codierung. " – jason

Antwort

8

BinaryWriter.Write(String) schreibt eine Länge Präfix Zeichenfolge zu diesem Stream. Das bedeutet, dass zuerst die Länge der Zeichenfolge in den Stream geschrieben wird und dann die Zeichenfolge mit einer Codierung. Die Länge wird jeweils zu sieben Bits kodiert, nicht als 32-Bit-Ganzzahl.

Wenn Sie aus dem Stream lesen möchten, sollten Sie BinaryReader.ReadString verwenden, die einen String mit Länge vor dem Stream liest.

+0

Wird automatisch auf den Rest der Daten gewartet, wenn er nicht im Stream vorhanden ist? – James

+0

Es schreibt nicht nur die Länge zuerst, sondern die Länge wird in einer 7-Bit-Codierung geschrieben. Also Zeichenfolgen, die weniger als 128 Byte lang sind, haben ein 1 Byte langes Präfix usw. –

+0

@James: Ja, es wird auf die Daten warten. –