30

Basically, I have been using both Integer.Parse and CInt in most of my daily programming tasks, but I'm a little bit confused of what the difference is between the two.

What is the difference between Integer.Parse and CInt in VB.NET?

Peter Mortensen
  • 30,738
  • 21
  • 105
  • 131
KG Sosa
  • 21,565
  • 6
  • 26
  • 27

4 Answers4

36

CInt does a whole lot more than Integer.Parse.

CInt will first check to see if what it was passed is an integer, and then simply casts it and returns it. If it's a double it will try to convert it without first converting the double to a string.

See this from the help for CInt and other Type Conversion Functions

Fractional Parts. When you convert a nonintegral value to an integral type, the integer conversion functions (CByte, CInt, CLng, CSByte, CShort, CUInt, CULng, and CUShort) remove the fractional part and round the value to the closest integer.

If the fractional part is exactly 0.5, the integer conversion functions round it to the nearest even integer. For example, 0.5 rounds to 0, and 1.5 and 2.5 both round to 2. This is sometimes called banker's rounding, and its purpose is to compensate for a bias that could accumulate when adding many such numbers together.

So in short, it does much more than convert a string to an integer, e.g. applying specific rounding rules to fractions, short circuiting unnecessary conversions etc.

If what you're doing is converting a string to an integer, use Integer.Parse (or Integer.TryParse), if you're coercing an unknown value (e.g. a variant or object from a database) to an integer, use CInt.

Binary Worrier
  • 50,774
  • 20
  • 136
  • 184
  • 4
    +1 but personally I would prefer using `DirectCast` or `TryCast` when coercing (casting) another type to an integer. I avoid `CInt` precisely because it's so flexible that IMHO it obscures the intent of the code. – MarkJ Nov 01 '12 at 12:10
  • 5
    @MarkJ: Sorry but I think you're confused mate, neither `DirectCast` or `TryCast` will convert a string to an integer, there must be an inheritance relationship for those to work. Maybe you're thinking of `TryCast` which will coerce an object to a integer, using the same rules as `CInt` – Binary Worrier Nov 01 '12 at 12:38
  • 3
    I'm saying nearly all the time, avoid using `CInt`. You wrote "if you are converting a string to an integer, use `*Parse`". Agree. I would then suggest that if you are starting from an integer type anyway (casting), just use `*Cast`. And only use `CInt` if you *really* don't know whether you are starting from an integer type or a string type. This last case should be very rare - getting a variant or an object from some kind of weakly typed data store that is used in an undisciplined way> – MarkJ Nov 01 '12 at 12:55
  • 1
    @MarkJ: Ah I see where you're coming from now. Although statements like _This last case should be very rare - getting a variant or an object from some kind of weakly typed data store that is used in an undisciplined way_, that really depends on the type of work you do, and the age of the code base you maintain :) – Binary Worrier Nov 01 '12 at 13:11
  • 1
    @BinaryWorrier: No need to back off. DirectCast only works if the object and the type are exactly the same, you can't cast an int to a long or vice-versa or from int to/from decimal. TryCast doesn't work value types, so you'll get a compiler error for trycast(0D, integer). The only choice for coercing from int to something else is the Cxxx functions or the System.Convert functions. – jmoreno Jan 31 '18 at 14:53
6

Looking with ILDASM at some sample code you can see that CInt is converted to this call:

Microsoft.VisualBasic]Microsoft.VisualBasic.CompilerServices.Conversions::ToInteger(string)

Using .NET Reflector, you can extract this piece of code:

Public Shared Function ToInteger(ByVal Value As String) As Integer
    Dim num As Integer
    If (Value Is Nothing) Then
        Return 0
    End If
    Try
        Dim num2 As Long
        If Utils.IsHexOrOctValue(Value, (num2)) Then
            Return CInt(num2)
        End If
        num = CInt(Math.Round(Conversions.ParseDouble(Value)))
    Catch exception As FormatException
        Throw New InvalidCastException(Utils.GetResourceString("InvalidCast_FromStringTo", New String() { Strings.Left(Value, &H20), "Integer" }), exception)
    End Try
    Return num
End Function

You can see that internally it calls Conversions.ParseDouble.

Therefore, as already explained by Binary Worrier, use Integer.Parse for string coercing and CInt only for casting.

Peter Mortensen
  • 30,738
  • 21
  • 105
  • 131
Drake
  • 8,225
  • 15
  • 71
  • 104
  • 1
    The documentation seems to imply that the compiler will treat CInt calls differently depending on how it's called, with different types as the parameter. I'd be interested to see what the compiler emits when Cint is passed an int, a long, a double etc. I'd expect calls with ints to be optimised out – Binary Worrier Jan 08 '09 at 12:58
  • i tried CInt with Int, Long, Double values and in this case the compiler optimize it automatically IL level. – Drake Jan 08 '09 at 14:50
  • This answer illustrates the pitfalls of using ILDASM rather than reading the documentation :) – MarkJ Nov 01 '12 at 12:07
  • 1
    This answer would be more useful if it had stated up front that the ILDASM was for the case where the incoming value was a String. You know that, and I can infer that, but the next reader coming along might find this answer confusing ;) – ToolmakerSteve Mar 19 '14 at 03:37
  • Nice to know if the value of a string is Nothing/null, it will return zero! – TamusJRoyce Feb 09 '15 at 22:06
  • I missed it, but the function does not take into consideration empty string: "" and crashes. C# type safety is so much more elegant... – TamusJRoyce Feb 09 '15 at 22:13
  • I'm confused. CInt is converted to a call to ToInteger, and ToInteger internally calls CInt? – motoDrizzt Sep 10 '18 at 12:48
0

Here is a real difference : Integer.parse("1.00") will thrown an error. CInt("1.00") will work

-1

The <Data Type>.Parse methods are used to extract a value of the type from a string that represents the value (e.g 2 from "2") The C<Data Type> functions operate on expressions and return a variant sub-typed to the desired type (e.g. CInt("2") OR CInt(SomeDouble + SomeDouble), etc.).

Jeff B
  • 8,572
  • 17
  • 61
  • 140
cmsjr
  • 56,771
  • 11
  • 70
  • 62
  • " . . . and return a Variant" in vb6 and previous versions yes, but NOT in .Net, they return specific types. – Binary Worrier Apr 07 '09 at 15:03
  • Yeah, I got sloppy and used a CInt definition from the .NET 3.0 Framework documentation that more specifically applies to VBScript http://msdn.microsoft.com/en-us/library/fctcwhw9(VS.85).aspx. – cmsjr Apr 07 '09 at 15:28
  • FYI, a "good" reference link would be "Type Conversion Functions (Visual Basic)": http://msdn.microsoft.com/en-us/library/s2dy91zy.aspx – ToolmakerSteve Mar 19 '14 at 03:42