Repository navigation
fix: honor StringComparison in Cut* string helpers - #2
Merged
Merged
Conversation
Every CutAfter, CutAfterLast, CutBefore and CutBeforeLast overload that
takes a StringComparison and returns a string or writes into a
destination compared ordinally. Only the CutSpan*/TryCutSpan*
overloads honored the comparison. For example,
"Hello World".CutAfter("WORLD", StringComparison.OrdinalIgnoreCase)
returned "Hello World" instead of "".
CutAfter and CutAfterLast also cut at index + needle.Length. With a
culture-sensitive comparison, the matched text can be longer or
shorter than the needle ("Å" matches "Å", a soft hyphen is
ignored), so they returned the wrong text or threw
ArgumentOutOfRangeException. They now cut after the actual match.
Co-Authored-By: Claude Opus 5.5 (xhigh) <noreply@anthropic.com>
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
Add this suggestion to a batch that can be applied as a single commit.This suggestion is invalid because no changes were made to the code.Suggestions cannot be applied while the pull request is closed.Suggestions cannot be applied while viewing a subset of changes.Only one suggestion per line can be applied in a batch.Add this suggestion to a batch that can be applied as a single commit.Applying suggestions on deleted lines is not supported.You must change the existing code in this line in order to create a valid suggestion.Outdated suggestions cannot be applied.This suggestion has been applied or marked resolved.Suggestions cannot be applied from pending reviews.Suggestions cannot be applied on multi-line comments.Suggestions cannot be applied while the pull request is queued to merge.Suggestion cannot be applied right now. Please check back later.
Every
CutAfter,CutAfterLast,CutBeforeandCutBeforeLastoverload that takes aStringComparisonand returns a string or writes into a destination ignored the comparison and matched ordinally. Only the span-returningCutSpan*/TryCutSpan*overloads honored it.The cause sits in the
ReadOnlySpan<char>extension blocks: theStringPooland destination overloads calledTryCutSpan*(needle, out cutValue)without passingcomparisonType. All other string-returning overloads route through those two.Culture-sensitive matches
CutAfterandCutAfterLastcut atindex + needle.Length. With a culture-sensitive comparison, the matched text can be longer or shorter than the needle. Examples withCutAfterandInvariantCulture:"xÅy""Å""̊y""y""xÅ""Å"ArgumentOutOfRangeException"""abcd"(soft hyphen)"bc""cd""d"For the four culture comparisons, they now use
CompareInfo.IndexOf/LastIndexOfwithout int matchLength.OrdinalandOrdinalIgnoreCasekeep theMemoryExtensionspath.CutBeforeandCutBeforeLastonly need the start index and were already correct.Validation
Tests added in
StringUtils.ExtTests.cs:CutAfter_String_Comparison,CutAfterLast_String_Comparison,CutBefore_String_Comparison,CutBeforeLast_String_Comparison:StringComparison, for string and span receiversStringPool, destination (also one char too small), spanOrdinalhas to fail andOrdinalIgnoreCasehas to matchCut_String_CultureMatchLength: the cases from the table, for all four culture comparisons and all four families.Cut_String_CurrentCulture: runs under tr-TR to tellCurrentCultureandInvariantCultureapart.CutSpan*on the string instead of.AsSpan()in 8 places.Checks run locally on Windows with SDK 11.0.100:
dotnet test -c Release: 108 passed on net10.0 and net11.0, 0 build warnings.master): all 9 fail on both target frameworks.The culture tests need ICU, which
ubuntu-latesthas. They would fail withInvariantGlobalization=true.🤖 Generated by Opus 5.5 (xhigh) with Claude Code in T3 Code