Here's a fairly painless way to down cast a long to an int, just extracting the low-order 32 bits without throwing an exception. No 64-bit division, no try/catch blocks, just bit twiddling and a single comparison.
Private Function CastLongToInt(x As Long) As Integer
Dim value As Integer = CType(x And &H7FFFFFFFL, Integer) ' get the low order 31 bits
' If bit 32 (the sign bit for a 32-bit signed integer is set, we OR it in
If (0 <> (x And &H80000000L)) Then
value = value Or &H80000000I
End If
Return value
End Function
Here's an ever simpler rendition — just bit-twiddling. No no comparisions at all. We just grab 2 16-bit nibbles and assemble them into the final value:
Private Function CastLongToInt(x As Long) As Integer
Dim hiNibble As Integer = &HFFFFL And (x >> 16)
Dim loNibble As Integer = &HFFFFL And x
Dim value As Integer = (hiNibble << 16) Or loNibble
Return value
End Function
Edited To Note:
Another option would be to use a nullable integer (System.Nullable<int>
). In VB.Net, it would be something like this:
Private Function TryCastLongToInt(x As Long) As Integer?
Dim value As Integer?
Try
value = CType(x, Integer)
Catch
' This exception intentionall swallowed here
End Try
Return value
End Function
Or, if the notion of intentionally catching and swallowing exceptions bugs you:
Private Function TryCastLongToInt(x As Long) As Integer?
If (x < Integer.MinValue) Then Return Nothing
If (x > Integer.MaxValue) Then Return Nothing
Return x
End Function
Either way, the return value will be either an integer value or Nothing
if the 64-bit value was outside the domain of a 32- bit integer.