@@ -3379,7 +3379,6 @@ public static void IndexOfSequenceLengthOneValue_Char()
33793379 Assert . Equal ( 2 , index ) ;
33803380 Assert . Equal ( index , s1 . IndexOf ( s2 , StringComparison . Ordinal ) ) ;
33813381
3382- // A zero-length value is always "found" at the start of the span.
33833382 ReadOnlySpan < char > span = s1 . AsSpan ( ) ;
33843383 ReadOnlySpan < char > value = s2 . AsSpan ( ) ;
33853384 index = span . IndexOf ( value ) ;
@@ -3396,7 +3395,6 @@ public static void IndexOfSequenceLengthOneValueAtVeryEnd_Char()
33963395 Assert . Equal ( 5 , index ) ;
33973396 Assert . Equal ( index , s1 . IndexOf ( s2 , StringComparison . Ordinal ) ) ;
33983397
3399- // A zero-length value is always "found" at the start of the span.
34003398 ReadOnlySpan < char > span = s1 . AsSpan ( ) ;
34013399 ReadOnlySpan < char > value = s2 . AsSpan ( ) ;
34023400 index = span . IndexOf ( value ) ;
@@ -3413,7 +3411,6 @@ public static void IndexOfSequenceLengthOneValueJustPasttVeryEnd_Char()
34133411 Assert . Equal ( - 1 , index ) ;
34143412 Assert . Equal ( index , s1 . IndexOf ( s2 , StringComparison . Ordinal ) ) ;
34153413
3416- // A zero-length value is always "found" at the start of the span.
34173414 ReadOnlySpan < char > span = s1 . AsSpan ( ) ;
34183415 ReadOnlySpan < char > value = s2 . AsSpan ( ) ;
34193416 index = span . IndexOf ( value ) ;
@@ -3887,18 +3884,23 @@ public static void LastIndexOf_AllSubstrings(string s, string value, int startIn
38873884
38883885 if ( value . Length == 0 )
38893886 {
3890- int expectedIndex = s . Length > 0 ? s . Length - 1 : 0 ;
3891- int expectedStartIndex = startIndex == s . Length ? startIndex - 1 : startIndex ;
3887+ int expectedStartIndex = startIndex ;
38923888 if ( s . Length == 0 && ( startIndex == - 1 || startIndex == 0 ) )
3893- expectedStartIndex = ( value . Length == 0 ) ? 0 : - 1 ;
3894- Assert . Equal ( expectedIndex , s . LastIndexOf ( value , comparison ) ) ;
3889+ expectedStartIndex = 0 ; // empty string occurs at beginning of search space
3890+ if ( s . Length > 0 && startIndex < s . Length )
3891+ expectedStartIndex = startIndex + 1 ; // empty string occurs just after the last char included in the search space
3892+
3893+ Assert . Equal ( s . Length , s . LastIndexOf ( value , comparison ) ) ;
38953894 Assert . Equal ( expectedStartIndex , s . LastIndexOf ( value , startIndex , comparison ) ) ;
3896- Assert . Equal ( expectedIndex , s . AsSpan ( ) . LastIndexOf ( value . AsSpan ( ) , comparison ) ) ;
3895+ Assert . Equal ( s . Length , s . AsSpan ( ) . LastIndexOf ( value . AsSpan ( ) , comparison ) ) ;
38973896 return ;
38983897 }
38993898
39003899 if ( s . Length == 0 )
39013900 {
3901+ // unit test shouldn't have passed a weightless string to this routine
3902+ Assert . NotEqual ( value , string . Empty , StringComparer . FromComparison ( comparison ) ) ;
3903+
39023904 Assert . Equal ( - 1 , s . LastIndexOf ( value , comparison ) ) ;
39033905 Assert . Equal ( - 1 , s . LastIndexOf ( value , startIndex , comparison ) ) ;
39043906 Assert . Equal ( - 1 , s . AsSpan ( ) . LastIndexOf ( value . AsSpan ( ) , comparison ) ) ;
@@ -4068,8 +4070,8 @@ public static void LastIndexOf_TurkishI_EnglishUSCulture()
40684070 }
40694071
40704072 [ Theory ]
4071- [ InlineData ( "foo" , 2 ) ]
4072- [ InlineData ( "hello" , 4 ) ]
4073+ [ InlineData ( "foo" , 3 ) ]
4074+ [ InlineData ( "hello" , 5 ) ]
40734075 [ InlineData ( "" , 0 ) ]
40744076 public static void LastIndexOf_EmptyString ( string s , int expected )
40754077 {
@@ -4325,13 +4327,13 @@ public static void LastIndexOfSequenceZeroLengthValue_Char()
43254327 string s1 = "0172377457778667789" ;
43264328 string s2 = string . Empty ;
43274329 int index = s1 . LastIndexOf ( s2 ) ;
4328- Assert . Equal ( s1 . Length - 1 , index ) ;
4330+ Assert . Equal ( s1 . Length , index ) ;
43294331
4330- // A zero-length value is always "found" at the start of the span.
4332+ // A zero-length value is always "found" at the end of the span.
43314333 ReadOnlySpan < char > span = s1 . AsSpan ( ) ;
43324334 ReadOnlySpan < char > value = s2 . AsSpan ( ) ;
43334335 index = span . LastIndexOf ( value ) ;
4334- Assert . Equal ( 0 , index ) ;
4336+ Assert . Equal ( span . Length , index ) ;
43354337 }
43364338
43374339 [ Fact ]
@@ -4356,7 +4358,6 @@ public static void LastIndexOfSequenceLengthOneValue_Char()
43564358 int index = s1 . LastIndexOf ( s2 ) ;
43574359 Assert . Equal ( 2 , index ) ;
43584360
4359- // A zero-length value is always "found" at the start of the span.
43604361 ReadOnlySpan < char > span = s1 . AsSpan ( ) ;
43614362 ReadOnlySpan < char > value = s2 . AsSpan ( ) ;
43624363 index = span . LastIndexOf ( value ) ;
@@ -4371,7 +4372,6 @@ public static void LastIndexOfSequenceLengthOneValueAtVeryEnd_Char()
43714372 int index = s1 . LastIndexOf ( s2 ) ;
43724373 Assert . Equal ( 5 , index ) ;
43734374
4374- // A zero-length value is always "found" at the start of the span.
43754375 ReadOnlySpan < char > span = s1 . AsSpan ( ) ;
43764376 ReadOnlySpan < char > value = s2 . AsSpan ( ) ;
43774377 index = span . LastIndexOf ( value ) ;
@@ -4386,7 +4386,6 @@ public static void LastIndexOfSequenceLengthOneValueMultipleTimes_Char()
43864386 int index = s1 . LastIndexOf ( s2 ) ;
43874387 Assert . Equal ( 5 , index ) ;
43884388
4389- // A zero-length value is always "found" at the start of the span.
43904389 ReadOnlySpan < char > span = s1 . AsSpan ( ) ;
43914390 ReadOnlySpan < char > value = s2 . AsSpan ( ) ;
43924391 index = span . LastIndexOf ( value ) ;
@@ -4401,7 +4400,6 @@ public static void LastIndexOfSequenceLengthOneValueJustPasttVeryEnd_Char()
44014400 int index = s1 . LastIndexOf ( s2 ) ;
44024401 Assert . Equal ( - 1 , index ) ;
44034402
4404- // A zero-length value is always "found" at the start of the span.
44054403 ReadOnlySpan < char > span = s1 . AsSpan ( ) ;
44064404 ReadOnlySpan < char > value = s2 . AsSpan ( ) ;
44074405 index = span . LastIndexOf ( value ) ;
0 commit comments