0

我有一个要求,我从字符串“111111”生成二进制数并将其转换为十进制数以存储在数据库中。这个二进制数的每个数字(即 1/0)表示用户对应用程序中不同模块的不同访问权限。随着模块数量的增加,这个二进制数的位数也会增加。当二进制数达到 64 的长度(即 64 乘以 1s)时,我能够使用将其转换为十进制数

Int64 dec =Convert.ToInt64(binVal,2);

它工作得很好。但是当长度增加到 65 时,它给出了溢出异常:对于 UInt64,值要么太大要么太小。任何人都可以提出任何可能的解决方案,我可以将这个长度为 65 的二进制数转换为十进制数或任何其他形式以将其保存在数据库中。

提前致谢。

4

2 回答 2

2

要将长度为 65 或更长的二进制数转换为十进制/无论您必须编写如下方法:

public BigInteger FromBinaryString(string binary)
{
    if (binary == null)
        throw new ArgumentNullException();
    if (!binary.All(c => c == '0' || c == '1'))
        throw new InvalidOperationException();

    BigInteger result = 0;
    foreach (var c in binary)
    {
        result <<= 1;
        result += (c - '0');
    }
    return result;
}

它使用System.Numerics.BigInteger结构来保存大数字。然后您可以将其显式转换为decimal(或字节数组)并将其存储在您的数据库中:

var bigInteger = FromBinaryString("100000000000000000000000000000000000000000000000000000000000000000");
// to decimal
var dec = (decimal)bigInteger;
// to byte array
var data = bigInteger.ToByteArray();

编辑:如果您在 NET 3.5 下,只需使用decimal而不是BigInteger(也将左移运算符替换为小数<<的乘法运算符):*

public decimal FromBinaryString(string binary)
{
    if (binary == null)
        throw new ArgumentNullException();
    if (!binary.All(c => c == '0' || c == '1'))
        throw new InvalidOperationException();

    decimal result = 0;
    foreach (var c in binary)
    {
        result *= 2;
        result += (c - '0');
    }
    return result;
}
于 2012-11-21T08:45:23.387 回答
1

在 SQL Server 或 C# 中,普通数字类型不适用于超过 64 位的数据。

您的其他选择包括:

  • 一个uniqueidentifier(GUID)字段,最多可提供 128 位。
  • 一个binaryvarbinary字段,它可以用于你可以想象的尽可能多的位。
  • 每个访问权限的单独位域。SQL Server 会自动将它们打包成字节。如果您将直接查询数据而不仅仅是持久化数据,这将是一个很好的选择。
  • 如前所述,一个字符串,但这将是对空间的严重浪费。
于 2012-11-21T07:20:01.763 回答