Isn't it interesting how the same code can appear to be both valid C# and VB.NET yet produce drastically different results? I did notice the lack of a trailing semicolon but assumed it was just a copy-and-paste artifact.
Using the following code...
Dim text As String = "Blah blah - WebSite - 9/20/2017 - Containers remaining changed to 0."
Dim list1 As List(Of String) = text.Split("Containers remaining changed to ").ToList()
...IntelliSense indicates that the String.Split(ParamArray() separator as Char())
overload is being called (the MSDN documentation includes the ParamArray
modifier)...

Upon execution list1
then contains the following:
list1(0) = "Blah blah - WebSite - 9/20/2017 - "
list1(1) = "ontainers remaining changed to 0."
If you write it using this seemingly-equivalent syntax...
Dim list2 As List(Of String) = text.Split("C", "o", "n", "t", "a", "i", "n", "e", "r", "s", " ", "r", "e", "m", "a", "i", "n", "i", "n", "g", " ", "c", "h", "a", "n", "g", "e", "d", " ", "t", "o", " ").ToList()
Dim list3 As List(Of String) = text.Split("Containers remaining changed to ".ToCharArray()).ToList()
...IntelliSense indicates both .Split()
calls are resolving to the same overload as above, yet the results for list2
are very different...
list2(0) = "Bl"
list2(1) = ""
list2(2) = ""
list2(3) = "bl"
list2(4) = ""
list2(5) = ""
list2(6) = "-"
list2(7) = "W"
list2(8) = "bS"
list2(9) = ""
list2(10) = ""
list2(11) = ""
list2(12) = "-"
list2(13) = "9/20/2017"
list2(14) = "-"
list2(15) = ""
list2(16) = ""
list2(17) = ""
list2(18) = ""
list2(19) = ""
list2(20) = ""
list2(21) = ""
list2(22) = ""
list2(23) = ""
list2(24) = ""
list2(25) = ""
list2(26) = ""
list2(27) = ""
list2(28) = ""
list2(29) = ""
list2(30) = ""
list2(31) = ""
list2(32) = ""
list2(33) = ""
list2(34) = ""
list2(35) = ""
list2(36) = ""
list2(37) = ""
list2(38) = ""
list2(39) = ""
list2(40) = ""
list2(41) = ""
list2(42) = ""
list2(43) = ""
list2(44) = ""
list2(45) = ""
list2(46) = ""
list2(47) = "0."
...and the same for list3
. This is actually what we should have expected list1
to be all along since it would split on any one of the characters in the passed String
.
Why is this happening? This is interesting to me, though I am not a VB.NET guy so perhaps this is common knowledge/pitfall. If we take a look at what the compiler produces we see this:
Dim text As String = "Blah blah - WebSite - 9/20/2017 - Containers remaining changed to 0."
Dim arg_13_0 As String = text
Dim expr_0E As Char() = New Char(0) {}
expr_0E(0) = "C"c
Dim list As List(Of String) = arg_13_0.Split(expr_0E).ToList(Of String)()
Dim arg_31_0 As String = text
Dim expr_26 As Char() = New Char(31) {}
RuntimeHelpers.InitializeArray(expr_26, fieldof(<PrivateImplementationDetails>.B46FB904AE74F7001A264BB77882D707B0E9ECC7).FieldHandle)
Dim list2 As List(Of String) = arg_31_0.Split(expr_26).ToList(Of String)()
Dim list3 As List(Of String) = text.Split("Containers remaining changed to ".ToCharArray()).ToList(Of String)()
That is, in the case of list2
it is passing a Char
array consisting of all of the Char
s in "Containers remaining changed to "
, yet in the case of list1
it is passing a Char
array consisting of only the first Char
, "C"c
! Talk about different results from similar-looking code...
I can't find a single document that connects all of these dots, but, basically, String
will be implicitly converted to Char()
, which calls the CChar
conversion function, which returns only the first Char
. Thus, the following four lines are equivalent:
Dim list1a As List(Of String) = text.Split("Containers remaining changed to ").ToList()
Dim list1b As List(Of String) = text.Split(CChar("Containers remaining changed to ")).ToList()
Dim list1c As List(Of String) = text.Split("C").ToList()
Dim list1d As List(Of String) = text.Split("C"c).ToList()