Skip to content

Fix Regex.EnumerateSplits ranges for capture groups, RightToLeft and empty matches - #642

Merged
SimonCropp merged 1 commit into
mainfrom
fix/regex-enumeratesplits
Oct 11, 2026
Merged

SimonCropp merged 1 commit into
mainfrom
fix/regex-enumeratesplits

Conversation

@SimonCropp

Copy link
Copy Markdown
Owner

Bug

The ValueSplitEnumerator polyfill (below net9.0) was built on Regex.Split and then tried to map the returned strings back to ranges. That goes wrong whenever Split does not correspond one-to-one with the gaps between matches:

  • Capture groups: Split includes captured text in its result, so new Regex("(-)").EnumerateSplits("a-b") yielded 0..1 2..3 3..4 (the last range is outside the 3 character input) instead of 0..1 2..3.
  • RegexOptions.RightToLeft: "," over "a,b,c" yielded 0..1 1..2 2..3 instead of 4..5 2..3 0..1.
  • Empty matches with RightToLeft came back in left-to-right order.

Fix

ValueSplitEnumerator now walks the matches lazily with Match/NextMatch and yields the range between consecutive matches, honouring count (the final permitted range is the remainder of the input) and startat, and walking from the end of the input for RightToLeft. Overloads without an explicit startat now start at the end of the input for RightToLeft regexes, as the BCL does.

Test

Added to PolyfillTests_Regex.cs, asserting the exact ranges (expected values taken from the real BCL): EnumerateSplits_CaptureGroups_NotIncluded, EnumerateSplits_RightToLeft, EnumerateSplits_CountAndStartat_Ranges and EnumerateSplits_EmptyMatches. Three of the four failed on net48 and net8.0 before the fix; all pass on net48 and net8.0 (polyfill) and net10.0 (BCL) after it.

Note: count: 1 is deliberately not covered. The BCL currently throws ArgumentOutOfRangeException from MoveNext in that case, which looks like a runtime bug; the polyfill returns the whole input as a single range.

@SimonCropp SimonCropp added this to the 11.4.4 milestone Oct 11, 2026
@SimonCropp
SimonCropp merged commit d2171c3 into main Oct 11, 2026
5 checks passed
@SimonCropp
SimonCropp deleted the fix/regex-enumeratesplits branch October 11, 2026 22:11
This was referenced Oct 12, 2026
This was referenced Oct 14, 2026
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

1 participant