转换为int类型将产生一个负数

本文关键字:一个 int 类型 转换 | 更新日期: 2023-09-27 18:19:22

我在设置FileStream中的位置时遇到了一个奇怪的错误:"需要非负数。参数名称:值".

public string this[Int64 index]
{
    get
    {
        Byte n = Convert.ToByte(0);
        Byte[] Buffer = new Byte[255];
        mem.Position = (int)(index * 256); //Error occurs here
        mem.Read(Buffer, 0, Buffer.Length);
        Buffer = (from b in Buffer where b != n select b).ToArray();
        return System.Text.Encoding.Default.GetString(Buffer);
    }
    set
    {
        mem.Position = (int)(index * 256);
        value += String.Concat(Enumerable.Repeat("'0", 255 - value.Length));
        Byte[] Buffer = System.Text.Encoding.Default.GetBytes(value + "|");
        mem.Write(Buffer, 0, Buffer.Length);
    }
}

作为一个long,索引的值为8,388,608,并且如预期的(index * 256) = 2,147,483,648,但是当我将其转换为int时,我得到的是相同的数字,只是负数。(-2147483648)。为什么会发生这种情况?

目标框架是。net 4,应用程序是为"任意CPU"构建的。

背景

如果有人想知道这段代码的目的,它是我写的一个类的一部分,它模仿字符串数组,但没有将值存储在内存中。MappedStringArray类允许我处理几乎任何大小的文件,而不会达到RAM限制,因为它只知道文件中行的位置,并在需要时读取它们。

转换为int类型将产生一个负数

整数溢出。2,147,483,648不能用int表示,其最大值为0。正值为2^31-1 = 2,147,483,647。(这是因为int在c#中是一个4字节= 32位的值,并且因为它是一个带符号的int,所以第一个位表示符号,留下31位作为实际数字)。

您可以看到2,147,483,648正好比它多1,因此int将溢出,将第一个位设置为1,表示负号,其余部分为零,因此,您将收到int可能的最大负数。

INT类型是有符号值。在代码中使用ULONG而不是INT。

 mem.Position = (Ulong)(index * 256); 

因为2,147,483,648是十六进制x80000000。就int32而言,这是个负数