Sqlserver
 sql >> Base de données >  >> RDS >> Sqlserver

SQL Server varbinary bigint avec les valeurs BitConverter.ToInt64 sont différentes

Diffuser depuis varbinary en bigint (et inversement) utilise l'ordre des octets du réseau (big-endian).BitConverter utilise l'endian-ness de la machine sur laquelle il est exécuté (little-endian pour x86 et x64).

D'où BitConverter.GetBytes exécuter sur -8588797048854775808 (0x88CE7696E7167800) est {0x00,0x88,0xE9,0x18,0x69,0x89,0x31,0x77}, et cast sur {0x00,0x88,0xE9,0x18,0x69,0x89,0x31,0x77} est 0x0088E91869893177 =38536887891734903.

La chose évidente à faire est de simplement stocker les entiers 64 bits en tant qu'entiers 64 bits en premier lieu.

Si vous avez vraiment besoin de faire cette conversion, alors :

var savedValue = BitConverter.GetBytes(IPAddress.HostToNetworkOrder(longValue))

Échangera les octets, tout en étant portable en ce sens qu'il n'échangera pas les octets s'il est exécuté sur une machine gros-boutiste.

Alternativement, si vous ne souhaitez pas utiliser l'espace de noms System.Net pour une raison quelconque, ou si vous souhaitez être extensible à des types autres que les trois IPAddress.HostToNetworkOrder poignées, utilisez :

var savedValue = BitConverter.GetBytes(longValue);
if(BitConverter.IsLittleEndian)
  Array.Reverse(savedValue);