web-dev-qa-db-fra.com

Comment convertir un int en un petit tableau d'octets endian?

J'ai cette fonction en C # pour convertir un petit tableau d'octets endian en un nombre entier:

int LE2INT(byte[] data)
{
  return (data[3] << 24) | (data[2] << 16) | (data[1] << 8) | data[0];
}

Maintenant, je veux le reconvertir en petit Endian .. Quelque chose comme

byte[] INT2LE(int data)
{
  // ...
}

Une idée?

Merci.

23
drowneath

Inverse-le, Notez que ce code (comme les autres) ne fonctionne que sur une petite machine Endian. (edit - c'était faux, car ce code retourne LE par définition)

  byte[] INT2LE(int data)
  {
     byte[] b = new byte[4];
     b[0] = (byte)data;
     b[1] = (byte)(((uint)data >> 8) & 0xFF);
     b[2] = (byte)(((uint)data >> 16) & 0xFF);
     b[3] = (byte)(((uint)data >> 24) & 0xFF);
     return b;
  }
19
John Knoeller

La classe BitConverter peut être utilisée pour cela, et bien sûr, elle peut également être utilisée à la fois sur les systèmes petit et grand. 

Bien sûr, vous devrez garder une trace du endianness de vos données. Pour les communications par exemple, cela serait défini dans votre protocole. 

Vous pouvez ensuite utiliser la classe BitConverter pour convertir un type de données en tableau d'octets et inversement, puis utiliser l'indicateur IsLittleEndian pour voir si vous devez le convertir sur votre système ou non.

Le drapeau IsLittleEndian vous indiquera le endianness du système, afin que vous puissiez l’utiliser comme suit:

Cela provient de la page MSDN de la classe BitConverter.

  int value = 12345678; //your value
  //Your value in bytes... in your system's endianness (let's say: little endian)
  byte[] bytes = BitConverter.GetBytes(value);
  //Then, if we need big endian for our protocol for instance,
  //Just check if you need to convert it or not:
  if (BitConverter.IsLittleEndian)
     Array.Reverse(bytes); //reverse it so we get big endian.

Vous pouvez trouver l'article complet ici .

J'espère que cela aide tous ceux qui viennent ici :)

18
Wracky

Il suffit de le faire à l'envers:

result[3]= (data >> 24) & 0xff;
result[2]= (data >> 16) & 0xff;
result[1]= (data >> 8)  & 0xff;
result[0]=  data        & 0xff; 
7
MSN

Pourriez-vous utiliser le BitConverter class? Je crois que cela ne fonctionnera que sur du matériel endian petit, mais il devrait supporter la plupart des tâches lourdes à votre place.

Voici un exemple artificiel illustrant l'utilisation de la classe:

        if(BitConverter.IsLittleEndian)
        {
            int someInteger = 100;
            byte[] bytes = BitConverter.GetBytes(someInteger);
            int convertedFromBytes = BitConverter.ToInt32(bytes, 0);
        }
3
Eric
BitConverter.GetBytes(1000).Reverse<byte>().ToArray();
2
Serban Lucian

Selon ce que vous faites réellement, vous pouvez vous permettre de laisser le cadre gérer les détails de l'endianité pour vous en utilisant IPAddress.HostToNetworkOrder et la fonction inverse correspondante. Ensuite, utilisez simplement la classe BitConverter pour accéder aux tableaux d'octets.

0
MikeP

Vous pouvez utiliser ceci si vous ne voulez pas utiliser de nouvelles allocations de tas:

public static void Int32ToFourBytes(Int32 number, out byte b0, out byte b1, out byte b2, out byte b3)
{
    b3 = (byte)number;
    b2 = (byte)(((uint)number >> 8) & 0xFF);
    b1 = (byte)(((uint)number >> 16) & 0xFF);
    b0 = (byte)(((uint)number >> 24) & 0xFF);
}
0
Mendi Barel
 public static string decimalToHexLittleEndian(int _iValue, int _iBytes)
    {
        string sBigEndian = String.Format("{0:x" + (2 * _iBytes).ToString() + "}", _iValue);
        string sLittleEndian = "";

        for (int i = _iBytes - 1; i >= 0; i--)
        {
            sLittleEndian += sBigEndian.Substring(i * 2, 2);
        }

        return sLittleEndian;
    }
0
Sean Campbell