【问题标题】:Sort objects in Java with case sensitive String key使用区分大小写的字符串键对 Java 中的对象进行排序
【发布时间】:2016-06-06 03:50:40
【问题描述】:

考虑到这种情况,我需要使用对象的名称(区域名称:字符串)对对象(区域)进行排序。我用 Java Comparator 接口试过这个。

class NameComparator implements Comparator<Zone> {
    public int compare(Zone z1, Zone z2) {
        return z1.getZoneName().compareTo(z2.getZoneName());
   }
}

但是这个 Comparator 只按字典顺序排序。

例如:区域名称的必需顺序。

['Zone AAa3','Zone aaa3','Zone BBB7','Zone BBb7','Zone bbb7']

电流输出:

['Zone AAa3','Zone BBB7','Zone BBb7','Zone aaa3','Zone bbb7']

除了写一个原始对象排序方法之外,还有什么方法可以实现吗?

【问题讨论】:

    标签: java sorting comparator


    【解决方案1】:

    有一个pre-defined comparator for case-insensitive sorting. 你可以用它和一个Zone by extracting a sort key.

    Comparator<Zone> byName = Comparator
        .comparing(Zone::getZoneName, String.CASE_INSENSITIVE_ORDER)
        .thenComparing(Zone::getZoneName);
    

    【讨论】:

    • 这似乎只适用于 Java 8。但看起来更简单。谢谢。
    • @shamikaDharmasiri 好吧,Java 7 在一年前就结束了支持(包括安全性),而 Java 9 也快到了。了解最新情况值得付出一些努力。
    • 但这并没有解决排序的用例('Zone AAa3'
    • @SubhrajyotiMajumder 已更新以处理该案例。
    • 每当你发现自己在写::compareTo时,你应该重新考虑你在做什么。 compareTo 方法的存在表明存在自然顺序,它允许使用Comparator.naturalOrder(),或者在大多数情况下完全省略比较器,即Comparator&lt;Zone&gt; byName = Comparator.comparing(Zone::getZoneName, String.CASE_INSENSITIVE_ORDER).thenComparing(Zone::getZoneName);。尽管在这种特定情况下,您可能希望改用 Comparator.comparing(Zone::getZoneName, Collator.getInstance())...
    【解决方案2】:

    调整逻辑,将名称转换为小写或大写,然后进行比较。

    public int compare(Zone z1, Zone z2){
      if(z1.getZoneName().toLowerCase().equals(z2.getZoneName().toLowerCase()))
          return z1.getZoneName().compareTo(z2.getZoneName());
      else
          return z1.getZoneName().toLowerCase().compareTo(z2.getZoneName().toLowerCase());
    }
    

    使用 lambda -

    Comparator<Zone> byName = (z1, z2)->{
        if(z1.getZoneName().toLowerCase().equals(z2.getZoneName().toLowerCase()))
           return z1.getZoneName().compareTo(z2.getZoneName());
        else
           return z1.getZoneName().toLowerCase().compareTo(z2.getZoneName().toLowerCase());
    };
    

    【讨论】:

    • 那么案件不考虑。我也需要考虑案件。我不能保证这个顺序,'Zone AAa3'
    • 更新答案 - 支持的用例 'Zone AAa3'
    • 转换为小写会不必要地浪费性能,并且可能无法涵盖所有​​ Unicode 字母的大小写。请注意 String.compareToIgnoreCase(String)String.equalsIgnoreCase(String) 的存在,它们执行所需的操作。
    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2012-06-25
    • 1970-01-01
    • 1970-01-01
    • 2011-12-01
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多