4

This might be a simple one, but I can't seem to find an easy way to do it. I need to save an array of 84 uint's into an SQL database's BINARY field. So I'm using the following lines in my C# ASP.NET project:

//This is what I have
uint[] uintArray;

//I need to convert from uint[] to byte[]
byte[] byteArray = ???

cmd.Parameters.Add("@myBindaryData", SqlDbType.Binary).Value = byteArray;

So how do you convert from uint[] to byte[]?

Robert Harvey
  • 178,213
  • 47
  • 333
  • 501
ahmd0
  • 16,633
  • 33
  • 137
  • 233

5 Answers5

10

How about:

byte[] byteArray = uintArray.SelectMany(BitConverter.GetBytes).ToArray();

This'll do what you want, in little-endian format...

Matt
  • 2,984
  • 1
  • 24
  • 31
  • Actually, this one would work. SelectMany does the iteration for you, but it will get all four bytes per int. It doesn't give you an easy solution to convert it back, though. – Random832 Nov 07 '11 at 04:37
  • @Random832 BitConverter.GetBytes returns 4 bytes per uint in any way. See examples on msdn http://msdn.microsoft.com/en-us/library/1184xdy4.aspx – hazzik Nov 07 '11 at 04:42
  • 1
    this may be elegant, however it will not be the fastest solution... you should really use buffer.blockcopy for the best performance. – Ben Childs Nov 23 '11 at 00:50
6

You can use System.Buffer.BlockCopy to do this:

byte[] byteArray = new byte[uintArray.Length * 4];
Buffer.BlockCopy(uintArray, 0, byteArray, 0, uintArray.Length * 4];

http://msdn.microsoft.com/en-us/library/system.buffer.blockcopy.aspx

This will be much more efficient than using a for loop or some similar construct. It directly copies the bytes from the first array to the second.

To convert back just do the same thing in reverse.

Ben Childs
  • 4,480
  • 1
  • 21
  • 9
3

There is no built-in conversion function to do this. Because of the way arrays work, a whole new array will need to be allocated and its values filled-in. You will probably just have to write that yourself. You can use the System.BitConverter.GetBytes(uint) function to do some of the work, and then copy the resulting values into the final byte[].

Here's a function that will do the conversion in little-endian format:

    private static byte[] ConvertUInt32ArrayToByteArray(uint[] value)
    {
        const int bytesPerUInt32 = 4;
        byte[] result = new byte[value.Length * bytesPerUInt32];
        for (int index = 0; index < value.Length; index++)
        {
            byte[] partialResult = System.BitConverter.GetBytes(value[index]);
            for (int indexTwo = 0; indexTwo < partialResult.Length; indexTwo++)
                result[index * bytesPerUInt32 + indexTwo] = partialResult[indexTwo];
        }
        return result;
    }
Jeffrey L Whitledge
  • 58,241
  • 9
  • 71
  • 99
  • OK, thanks I guess I need to reiterate through them and call System.BitConverter.GetBytes(uint) on each value of uint[] array. – ahmd0 Nov 07 '11 at 04:28
  • 2
    Can be rewritten using LINQ as `byte[] byteArray = uintArray.SelectMany(o => BitConverter.GetBytes(o)).ToArray();` – Ilia G Nov 07 '11 at 04:32
  • @liho1eye - Yes, I like that solution. I especially like the fact that if you change from a `uint[]` to a `short[]` or a `ulong[]` or whatever, the code doesn't need to be changed. – Jeffrey L Whitledge Nov 07 '11 at 15:39
1
byte[] byteArray = Array.ConvertAll<uint, byte>(
    uintArray,
    new Converter<uint, byte>(
        delegate(uint u) { return (byte)u; }
    ));

Heed advice from @liho1eye, make sure your uints really fit into bytes, otherwise you're losing data.

ssamuel
  • 427
  • 3
  • 6
0

If you need all the bits from each uint, you're gonna to have to make an appropriately sized byte[] and copy each uint into the four bytes it represents.

Something like this ought to work:

uint[] uintArray;

//I need to convert from uint[] to byte[]
byte[] byteArray = new byte[uintArray.Length * sizeof(uint)];
for (int i = 0; i < uintArray.Length; i++)
{
    byte[] barray = System.BitConverter.GetBytes(uintArray[i]);
    for (int j = 0; j < barray.Length; j++)
    {
          byteArray[i * sizeof(uint) + j] = barray[j];
    }
}
cmd.Parameters.Add("@myBindaryData", SqlDbType.Binary).Value = byteArray;
akatakritos
  • 9,836
  • 1
  • 23
  • 29