从BigInteger到固定大小整数的标准转换都会在数字太大时抛出OverflowException(以及unchecked doesn't work)。如何获得类似unchecked的转换行为?
BigInteger
OverflowException
unchecked
js5cn81o1#
您可以通过屏蔽高位来截断BigInteger。例如,给定BigInteger big:
BigInteger big
(uint)(big & uint.MaxValue)
uint
(ulong)(big & ulong.MaxValue)
ulong
unchecked((int)(uint)(big & uint.MaxValue))
int
unchecked((long)(ulong)(big & ulong.MaxValue))
long
这种技术效率不高;它需要两次内存分配(一个用于将uint.MaxValue转换为BigInteger,另一个用于保存&操作的结果).但是我看不出有其他的方法.然而,当掩码小于32位时(例如,用(ushort)(big & ushort.MaxValue)转换为ushort不应分配内存),因为BigInteger不为31位或更小的数字分配内存。
uint.MaxValue
&
(ushort)(big & ushort.MaxValue)
ushort
odopli942#
更快的方法:
public static int ToInt(this BigInteger big) { return BitConverter.ToInt32(big.ToByteArray().AsSpan(0, 4)); }
long、uint等的解决方案非常简单。
2条答案
按热度按时间js5cn81o1#
您可以通过屏蔽高位来截断
BigInteger
。例如,给定BigInteger big
:(uint)(big & uint.MaxValue)
转换为uint
(ulong)(big & ulong.MaxValue)
转换为ulong
unchecked((int)(uint)(big & uint.MaxValue))
转换为int
unchecked((long)(ulong)(big & ulong.MaxValue))
转换为long
这种技术效率不高;它需要两次内存分配(一个用于将
uint.MaxValue
转换为BigInteger
,另一个用于保存&
操作的结果).但是我看不出有其他的方法.然而,当掩码小于32位时(例如,用(ushort)(big & ushort.MaxValue)
转换为ushort
不应分配内存),因为BigInteger
不为31位或更小的数字分配内存。odopli942#
更快的方法:
long
、uint
等的解决方案非常简单。