I was searching for a way to check whether I've reached the end of a file for my binary reader and one suggestion was to use PeekChar as such
while (inFile.PeekChar() > 0)
{
...
}
However, it looks like I've run into an issue
Unhandled Exception: System.ArgumentException: The output char buffer is too sma ll to contain the decoded characters, encoding 'Unicode (UTF-8)' fallback 'Syste m.Text.DecoderReplacementFallback'. Parameter name: chars at System.Text.Encoding.ThrowCharsOverflow() at System.Text.Encoding.ThrowCharsOverflow(DecoderNLS decoder, Boolean nothin gDecoded) at System.Text.UTF8Encoding.GetChars(Byte* bytes, Int32 byteCount, Char* char s, Int32 charCount, DecoderNLS baseDecoder) at System.Text.DecoderNLS.GetChars(Byte* bytes, Int32 byteCount, Char* chars, Int32 charCount, Boolean flush) at System.Text.DecoderNLS.GetChars(Byte[] bytes, Int32 byteIndex, Int32 byteC ount, Char[] chars, Int32 charIndex, Boolean flush) at System.Text.DecoderNLS.GetChars(Byte[] bytes, Int32 byteIndex, Int32 byteC ount, Char[] chars, Int32 charIndex) at System.IO.BinaryReader.InternalReadOneChar() at System.IO.BinaryReader.PeekChar()
So maybe PeekChar isn't the best way to do it, and I don't think it should even be used that way because I'm checking the current position of my reader and not really what the next character is supposed to be.
There is a more accurate way to check for EOF when working with binary data. It avoids all of the encoding issues that come with the PeekChar
approach and does exactly what is needed: to check whether the position of the reader is at the end of the file or not.
while (inFile.BaseStream.Position != inFile.BaseStream.Length)
{
...
}
Wrapping it into a Custom Extension Method that'll extend the BinaryReader class by adding the missing EOF method.
public static class StreamEOF {
public static bool EOF( this BinaryReader binaryReader ) {
var bs = binaryReader.BaseStream;
return ( bs.Position == bs.Length);
}
}
So now you can just write:
while (!infile.EOF()) {
// Read....
}
:) ... assuming you have created infile somewhere like this:
var infile= new BinaryReader();
Note: var is implicit typing. Happy to found it - it's other puzzle piece for well styled code in C#. :D
This work for me:
using (BinaryReader br = new BinaryReader(File.Open(fileName,
FileMode.Open))) {
//int pos = 0;
//int length = (int)br.BaseStream.Length;
while (br.BaseStream.Position != br.BaseStream.Length) {
string nume = br.ReadString ();
string prenume = br.ReadString ();
Persoana p = new Persoana (nume, prenume);
myArrayList.Add (p);
Console.WriteLine ("ADAUGAT XXX: "+ p.ToString());
//pos++;
}
}
I'll add my suggestion: if you don't need the "encoding" part of the BinaryReader (so you don't use the various ReadChar/ReadChars/ReadString) then you can use an encoder that won't ever throw and that is always one-byte-per-char. Encoding.GetEncoding("iso-8859-1")
is perfect for this. You pass it as a parameter of the BinaryReader
constructor. The iso-8859-1 encoding is a one-byte-per-character encoding that maps 1:1 all the first 256 characters of Unicode (so the byte
254 is the char
254 for example)
来源:https://stackoverflow.com/questions/10942848/c-sharp-checking-for-binary-reader-end-of-file