使用 int 数据类型在 C# 中添加大数字时出现问题
Issue in Adding large numbers in C# with int datatype
我正在尝试使用 int
数据类型在 C#
中添加五个大数。但结果并不正确。为什么 .net
迫使我转换为 long
并执行添加以获得正确的结果。
using System;
public class Program
{
public static void Main()
{
int i1= 256741038,i2= 623958417,i3= 467905213 ,i4= 714532089,i5=938071625;
long l1= 256741038,l2= 623958417,l3= 467905213 ,l4= 714532089,l5=938071625;
long result1=i2+i3+i4+i5;
long result2=l2+l3+l4+l5;
long result3=(long)l2+(long)l3+(long)l4+(long)l5;
Console.WriteLine(result1);
Console.WriteLine(result2);
Console.WriteLine(result3);
}
}
int
有一个 maximum value of 2,147,483,647。如果您尝试创建一个大于此的 int
(例如,通过添加两个更小的 ints
),它将环绕成一个非常大的负数。这就是 result1
.
中发生的事情
long
更大,最大值为 9,223,372,036,854,775,807。这足以容纳您要表示的值。
由于性能 C#(不是 dotnet)和我知道的任何其他语言都使用最大的公分母来执行操作。这在他们之间很常见。不是结果,这是必须猜测的。
所以,添加2个int数是一个可能溢出的int操作。将 int 添加到 long 是一个很长的操作。添加两个long是一个long操作。
就这么简单。如果您知道会溢出,则将其中一种类型声明为更长。
现在,您可以施放 - 您也可以将它们声明为 long,你知道的。
C# short/long/int literal format?
向您展示了所有足够的内容。
- 1111 是一个整数
- 1111UL 是一个无符号长整数。
因此,如果您告诉编译器要在文字中使用正确的数据类型,则无需强制转换。
您可以使用 checked
keyword 查看 long result1=i2+i3+i4+i5;
正在生成 System.OverflowException: 'Arithmetic operation resulted in an overflow.'
,正如其他答案所说。您的操作的有效结果是 2,744,467,344,但 int 的最大值(即 Int32)是 2,147,483,647。 Long 类型(Int64 的别名)最多可以包含 9,223,372,036,854,775,807,这足以添加您的数字而不会溢出。
public static void Main()
{
checked
{
int i1 = 256741038, i2 = 623958417, i3 = 467905213, i4 = 714532089, i5 = 938071625;
long l1 = 256741038, l2 = 623958417, l3 = 467905213, l4 = 714532089, l5 = 938071625;
long result1 = i2 + i3 + i4 + i5;
long result2 = l2 + l3 + l4 + l5;
long result3 = (long)l2 + (long)l3 + (long)l4 + (long)l5;
Console.WriteLine(result1);
Console.WriteLine(result2);
Console.WriteLine(result3);
Console.Read();
}
}
除了少数例外,C# 中的类型解析并不关心您分配给 给 的类型。在您的情况下,编译器正在考虑的所有内容是
i2 + i3 + i4 + i5
因为每个操作数都是 int
类型,结果是 also 类型 int
(或者,更准确地说,它使用加法以两个 int
作为参数和 returns int
) 的运算符,即使您稍后将其分配给 long
local.
通过将其中一个操作数转换为 long
,int, int -> int
运算符不再适用,因此选择了 long, long -> long
。 float
也是如此,例如 - 只要其中一个操作数是 float
,结果就是 float
- 否则,a / b
会给出整数除法(运算符int, int -> int
).
一般来说,您需要确保您使用的数据类型足够大以容纳结果和任何中间值。如果您期望的结果不适合 int
,请不要使用 int
。默认情况下,C# 不检查溢出 - 您可以像这样覆盖它:
var result = checked(i2 + i3 + i4 + i5);
这样,您将得到一个异常,而不是默默地回绕到错误的 int
值。
我正在尝试使用 int
数据类型在 C#
中添加五个大数。但结果并不正确。为什么 .net
迫使我转换为 long
并执行添加以获得正确的结果。
using System;
public class Program
{
public static void Main()
{
int i1= 256741038,i2= 623958417,i3= 467905213 ,i4= 714532089,i5=938071625;
long l1= 256741038,l2= 623958417,l3= 467905213 ,l4= 714532089,l5=938071625;
long result1=i2+i3+i4+i5;
long result2=l2+l3+l4+l5;
long result3=(long)l2+(long)l3+(long)l4+(long)l5;
Console.WriteLine(result1);
Console.WriteLine(result2);
Console.WriteLine(result3);
}
}
int
有一个 maximum value of 2,147,483,647。如果您尝试创建一个大于此的 int
(例如,通过添加两个更小的 ints
),它将环绕成一个非常大的负数。这就是 result1
.
long
更大,最大值为 9,223,372,036,854,775,807。这足以容纳您要表示的值。
由于性能 C#(不是 dotnet)和我知道的任何其他语言都使用最大的公分母来执行操作。这在他们之间很常见。不是结果,这是必须猜测的。
所以,添加2个int数是一个可能溢出的int操作。将 int 添加到 long 是一个很长的操作。添加两个long是一个long操作。
就这么简单。如果您知道会溢出,则将其中一种类型声明为更长。
现在,您可以施放 - 您也可以将它们声明为 long,你知道的。
C# short/long/int literal format?
向您展示了所有足够的内容。
- 1111 是一个整数
- 1111UL 是一个无符号长整数。
因此,如果您告诉编译器要在文字中使用正确的数据类型,则无需强制转换。
您可以使用 checked
keyword 查看 long result1=i2+i3+i4+i5;
正在生成 System.OverflowException: 'Arithmetic operation resulted in an overflow.'
,正如其他答案所说。您的操作的有效结果是 2,744,467,344,但 int 的最大值(即 Int32)是 2,147,483,647。 Long 类型(Int64 的别名)最多可以包含 9,223,372,036,854,775,807,这足以添加您的数字而不会溢出。
public static void Main()
{
checked
{
int i1 = 256741038, i2 = 623958417, i3 = 467905213, i4 = 714532089, i5 = 938071625;
long l1 = 256741038, l2 = 623958417, l3 = 467905213, l4 = 714532089, l5 = 938071625;
long result1 = i2 + i3 + i4 + i5;
long result2 = l2 + l3 + l4 + l5;
long result3 = (long)l2 + (long)l3 + (long)l4 + (long)l5;
Console.WriteLine(result1);
Console.WriteLine(result2);
Console.WriteLine(result3);
Console.Read();
}
}
除了少数例外,C# 中的类型解析并不关心您分配给 给 的类型。在您的情况下,编译器正在考虑的所有内容是
i2 + i3 + i4 + i5
因为每个操作数都是 int
类型,结果是 also 类型 int
(或者,更准确地说,它使用加法以两个 int
作为参数和 returns int
) 的运算符,即使您稍后将其分配给 long
local.
通过将其中一个操作数转换为 long
,int, int -> int
运算符不再适用,因此选择了 long, long -> long
。 float
也是如此,例如 - 只要其中一个操作数是 float
,结果就是 float
- 否则,a / b
会给出整数除法(运算符int, int -> int
).
一般来说,您需要确保您使用的数据类型足够大以容纳结果和任何中间值。如果您期望的结果不适合 int
,请不要使用 int
。默认情况下,C# 不检查溢出 - 您可以像这样覆盖它:
var result = checked(i2 + i3 + i4 + i5);
这样,您将得到一个异常,而不是默默地回绕到错误的 int
值。