I'm currently writing a binary reader that reads a value from a BinaryReader
at a given position. For that I have to store the current position of the MemoryStream
so I can restore it afterwards.
public byte GetByte(int position)
{
long oldPosition = this.memoryStream.Position;
this.memoryStream.Position = position;
byte value = this.ReadByte();
this.memoryStream.Position = oldPosition;
return value;
}
EDIT: As requested, more similar functions:
public byte[] GetByteArray(int position, int length)
{
long oldPosition = this.memoryStream.Position;
this.memoryStream.Position = position;
byte[] value = this.ReadByteArray(length);
this.memoryStream.Position = oldPosition;
return value;
}
public bool GetBoolean(int position)
{
long oldPosition = this.memoryStream.Position;
this.memoryStream.Position = position;
bool value = this.ReadBoolean();
this.memoryStream.Position = oldPosition;
return value;
}
public ushort GetUInt16(int position)
{
long oldPosition = this.memoryStream.Position;
this.memoryStream.Position = position;
ushort value = this.ReadUInt16();
this.memoryStream.Position = oldPosition;
return value;
}
and so on..
Is there any way to shorten this process and avoid doubled-code since I have many functions similar to that?
1 Answer 1
Try a pair of methods like this:
public T GetValue<T>(int position, Func<T> readFunc)
{
long oldPosition = this.memoryStream.Position;
this.memoryStream.Position = position;
T value = readFunc();
this.memoryStream.Position = oldPosition;
return value;
}
public T GetValue<T>(int position, Func<int, T> readFunc, int length)
{
long oldPosition = this.memoryStream.Position;
this.memoryStream.Position = position;
T value = readFunc(length);
this.memoryStream.Position = oldPosition;
return value;
}
then they can be called as such:
byte b = GetValue(position, ReadByte);
byte[] ba = GetValue(position, ReadByteArray, length);
// etc.
ETA: I might write the methods like this to ensure the stream's position gets reset properly, even in the event of an exception:
public T GetValue<T>(int position, Func<T> readFunc)
{
var oldPosition = this.memoryStream.Position;
this.memoryStream.Position = position;
try
{
return readFunc();
}
finally
{
this.memoryStream.Position = oldPosition;
}
}
public T GetValue<T>(int position, Func<int, T> readFunc, int length)
{
var oldPosition = this.memoryStream.Position;
this.memoryStream.Position = position;
try
{
return readFunc(length);
}
finally
{
this.memoryStream.Position = oldPosition;
}
}
Stream.Position
. If you can be assured that it's only ever aMemoryStream
that you'll be working with, you could produce a thread-safe implementation by working with thebyte
array (MemoryStream.GetBuffer()
) and using BitConverter to read values. \$\endgroup\$