user817746
user817746

Reputation: 23

C#: How to get typed variable from value in Object variable and type in Type variable?

  1. I have a value in a variable of type Object.
  2. I have its type in a variable of type Type.
  3. Type can be only among standard system types (Int32, Int64, etc..)

Q. I want to get bytes array representing this value. I'm trying to use BitConverter.GetBytes for that, but it requires a typed variable. Is there a way to get typed variable dynamically having a value and type in separate variables?

Thank you.

Upvotes: 2

Views: 436

Answers (5)

Magnus
Magnus

Reputation: 46997

You can use MemoryMappedFile

private byte[] GetBytes<T>(T obj) where T : struct
{
    int size = Marshal.SizeOf(typeof(T));
    using(var mmf = MemoryMappedFile.CreateNew("test", size))
    using(var acc = mmf.CreateViewAccessor())
    {
        acc.Write(0, ref obj);
        var arr = new byte[size];
        for (int i = 0; i < size; i++)
            arr[i] = acc.ReadByte(i);
        return arr;
    }
}

Upvotes: 0

Mike Caron
Mike Caron

Reputation: 14561

public byte[] GetAnyBytes(dynamic myVariable) {
     return BitConverter.GetBytes(myVariable)
}

dynamic is essentially "I don't know what type this could be, check it at run time". Obviously, this is slower than using real types, but it is more flexible. Also, requires C# 4.0.

Upvotes: 2

dpurrington
dpurrington

Reputation: 1533

I'm concerned that you're trying to interact with another device using a binary format. Assuming the receiver of your data is not .NET, binary representations of data types varies from one device to another. I think you're better off representing this information in text, and using a parser to interpret the text.

Upvotes: 0

Allon Guralnek
Allon Guralnek

Reputation: 16131

If you don't want to switch on each type and call the appropriate method, which is the fastest way, you could use reflection, albeit a bit slower:

byte[] GetBytes(object obj)
{
    var type = obj.GetType();
    return (byte[])typeof(BitConverter)
        .GetMethods(BindingFlags.Public | BindingFlags.Static)
        .Single(m => m.Name == "GetBytes" && m.GetParameters().Single().ParameterType == type)
        .Invoke(null, new object[] { obj });
}

Calling GetBytes((short)12345) produces new byte[] { 0x39 ,0x30 }.

Upvotes: 2

lincolnk
lincolnk

Reputation: 11238

You could try something like this to get a byte array.

public static byte[] Object2ByteArray(object o)
{
    using (System.IO.MemoryStream ms = new System.IO.MemoryStream())
    {
        System.Runtime.Serialization.Formatters.Binary.BinaryFormatter bf = 
            new System.Runtime.Serialization.Formatters.Binary.BinaryFormatter();
        bf.Serialize(ms, o);
        return ms.ToArray();
    }
}

Although based on your description you may have made some poor implementation choices elsewhere.

found here.

Upvotes: 1

Related Questions