diff options
| author | Bond-009 <bond.009@outlook.com> | 2020-03-02 12:28:31 +0100 |
|---|---|---|
| committer | GitHub <noreply@github.com> | 2020-03-02 12:28:31 +0100 |
| commit | 1c21248e2e10b292a890cb10a34cc26c2f34643e (patch) | |
| tree | 338e102269f93754eb7c81086fd5e1598c3211b7 /MediaBrowser.Controller/Sorting/AlphanumComparator.cs | |
| parent | 13d30a0a793de09862a725e6c7581fa70c10e034 (diff) | |
| parent | 376bbb40bdc4f68c61416855fd807fc4b68fbc92 (diff) | |
Merge pull request #2474 from JustAMan/simplify-sorting
Simplify AlphanumericComparer, reduce code duplication
Diffstat (limited to 'MediaBrowser.Controller/Sorting/AlphanumComparator.cs')
| -rw-r--r-- | MediaBrowser.Controller/Sorting/AlphanumComparator.cs | 97 |
1 files changed, 97 insertions, 0 deletions
diff --git a/MediaBrowser.Controller/Sorting/AlphanumComparator.cs b/MediaBrowser.Controller/Sorting/AlphanumComparator.cs new file mode 100644 index 000000000..65dc120ca --- /dev/null +++ b/MediaBrowser.Controller/Sorting/AlphanumComparator.cs @@ -0,0 +1,97 @@ +using System.Collections.Generic; +using System.Text; +using MediaBrowser.Controller.Sorting; + +namespace MediaBrowser.Controller.Sorting +{ + public class AlphanumComparator : IComparer<string> + { + public static int CompareValues(string s1, string s2) + { + if (s1 == null || s2 == null) + { + return 0; + } + + int thisMarker = 0, thisNumericChunk = 0; + int thatMarker = 0, thatNumericChunk = 0; + + while ((thisMarker < s1.Length) || (thatMarker < s2.Length)) + { + if (thisMarker >= s1.Length) + { + return -1; + } + else if (thatMarker >= s2.Length) + { + return 1; + } + char thisCh = s1[thisMarker]; + char thatCh = s2[thatMarker]; + + var thisChunk = new StringBuilder(); + var thatChunk = new StringBuilder(); + bool thisNumeric = char.IsDigit(thisCh), thatNumeric = char.IsDigit(thatCh); + + while (thisMarker < s1.Length && char.IsDigit(thisCh) == thisNumeric) + { + thisChunk.Append(thisCh); + thisMarker++; + + if (thisMarker < s1.Length) + { + thisCh = s1[thisMarker]; + } + } + + while (thatMarker < s2.Length && char.IsDigit(thatCh) == thatNumeric) + { + thatChunk.Append(thatCh); + thatMarker++; + + if (thatMarker < s2.Length) + { + thatCh = s2[thatMarker]; + } + } + + + // If both chunks contain numeric characters, sort them numerically + if (thisNumeric && thatNumeric) + { + if (!int.TryParse(thisChunk.ToString(), out thisNumericChunk) + || !int.TryParse(thatChunk.ToString(), out thatNumericChunk)) + { + return 0; + } + + if (thisNumericChunk < thatNumericChunk) + { + return -1; + } + + if (thisNumericChunk > thatNumericChunk) + { + return 1; + } + } + else + { + int result = thisChunk.ToString().CompareTo(thatChunk.ToString()); + if (result != 0) + { + return result; + } + } + + } + + return 0; + } + + public int Compare(string x, string y) + { + return CompareValues(x, y); + } + } +} |
