X-Git-Url: https://mograsim.net/gitweb/?a=blobdiff_plain;f=plugins%2Fnet.mograsim.plugin.core%2Fsrc%2Fnet%2Fmograsim%2Fplugin%2Futil%2FNumberRespectingStringComparator.java;fp=plugins%2Fnet.mograsim.plugin.core%2Fsrc%2Fnet%2Fmograsim%2Fplugin%2Futil%2FNumberRespectingStringComparator.java;h=c2deaf76f5041cb7315674f35ec019fc158fe234;hb=f8f69ae61db66e701388f07bf0e3da493790fe45;hp=0000000000000000000000000000000000000000;hpb=7924a5555f5b194919c0293e8560517a096cfb92;p=Mograsim.git diff --git a/plugins/net.mograsim.plugin.core/src/net/mograsim/plugin/util/NumberRespectingStringComparator.java b/plugins/net.mograsim.plugin.core/src/net/mograsim/plugin/util/NumberRespectingStringComparator.java new file mode 100644 index 00000000..c2deaf76 --- /dev/null +++ b/plugins/net.mograsim.plugin.core/src/net/mograsim/plugin/util/NumberRespectingStringComparator.java @@ -0,0 +1,55 @@ +package net.mograsim.plugin.util; + +import java.math.BigInteger; +import java.util.Comparator; +import java.util.regex.Matcher; +import java.util.regex.Pattern; + +/** + * Compares Strings respecting integers that appear in the strings with positions in common.
+ * Note that 0003 , 03 and 3 are considered to be at the same level; however if there is no further difference, lexicographic ordering is + * applied to ensure the comparator meets the {@link Comparator contract} (this will sort "foor_02" before "foo_2"). + * + * @author Christian Femers + * + */ +public class NumberRespectingStringComparator implements Comparator +{ + public static final NumberRespectingStringComparator CASE_SENSITIVE = new NumberRespectingStringComparator(); + + private static final Pattern PATTERN = Pattern.compile("\\d+", Pattern.DOTALL); + + private final Comparator comp = CharSequence::compare; + + private NumberRespectingStringComparator() + { + } + + @Override + public int compare(String o1, String o2) + { + Matcher m1 = PATTERN.matcher(o1); + Matcher m2 = PATTERN.matcher(o2); + int pos1 = 0; + int pos2 = 0; + while (m1.find() && m2.find() && m1.start() - pos1 == m2.start() - pos2) + { + int charsCompRes = comp.compare(o1.subSequence(pos1, m1.start()), o2.subSequence(pos2, m2.start())); + if (charsCompRes != 0) + return charsCompRes; + + BigInteger num1 = new BigInteger(m1.group()); + BigInteger num2 = new BigInteger(m2.group()); + int compRes = num1.compareTo(num2); + if (compRes != 0) + return compRes; + + pos1 = m1.end(); + pos2 = m2.end(); + } + int restCompRes = comp.compare(o1.substring(pos1), o2.substring(pos2)); + if (restCompRes != 0) + return restCompRes; + return comp.compare(o1, o2); + } +}