Java 安卓列表字符串带有数字和国家/地区字母的排序字符串
我无法将我的字符串与我想要的地址进行排序Ąraków Medyczna 1 Kraków Medyczna 2,Kraków Medyczna 13。但在第一个我有:克拉科夫医学院2号,克拉科夫医学院13号,卡拉科夫医学院1号,第二个我有:克拉科夫医学院1号,克拉科夫医学院13号,克拉科夫医学院2号
ArrayList<String> names = new ArrayList<String>();
names.add("Kraków, Medyczna 13");
names.add("Ąraków, Medyczna 1");
names.add("Kraków, Medyczna 2");
Collections.sort(names);
Collections.sort(names, Collator.getInstance(new Locale("PL")));
for(String s : names){
System.out.println(s);
}
Collections.sort(names, new Comparator<String>() {
public int compare(String o1, String o2) {
String o1StringPart = o1.replaceAll("\\d", "");
String o2StringPart = o2.replaceAll("\\d", "");
if(o1StringPart.equalsIgnoreCase(o2StringPart))
{
return extractInt(o1) - extractInt(o2);
}
return o1.compareTo(o2);
}
int extractInt(String s) {
String num = s.replaceAll("\\D", "");
// return 0 if no digits found
return num.isEmpty() ? 0 : Integer.parseInt(num);
}
});
for(String s : names){
System.out.println(s);
}
# 1 楼答案
您希望逐部分比较完全由数字(数字)和完全由非数字(文本)组成的部分
下面的比较循环(文本、数字?)
如果只有一个字符串以数字开头,那么它的第一部分是一个空文本,将被认为更小
在java 8中,使用所谓的lambda:
这相当冗长,自java 9以来有一个“简单”的解决方案: 只需将所有数字格式化为固定宽度,在这里用零填充最多10个位置
由于java 9,有一个重载的
String.replaceAll
可以传递给替换函数如果不重复一个自我,那就更优雅了:
最后,对于任何转换,或者传递一个字段的getter,都有一个实用函数:
Comparator.comparing(converter)
和Comparator.comparing(converter, otherComparator)
要按您的地区/语言对其进行排序:
Collator是一个比较器,但具有给定语言的内置排序功能。它在重音字母上表现得更好。我在这里放弃了不区分大小写的比较,因为它可能不需要;否则使用
String.toUpperCase(Locale)
这有点过分,我不完全确定Android的java,或者代码是否可以编译(拼写错误),但我很喜欢
# 2 楼答案
您的自定义比较器几乎没有问题,只是忘记了对波兰字符集使用正确的比较器。在正常字符串比较中,“Ą”位于“K”之后
改变
到