按多个属性对ArrayList进行排序

时间:2015-05-04 08:06:20

标签: java sorting arraylist comparator

我有一个ArrayList名玩家,其属性为username类型字符串,winratio类型为long,只是gameswon/gamesplayed*100的比率。

我想要使用ArrayList类对我已经完成的username Comparator进行排序,但我还想制作另一种方法,根据{{1}对玩家进行排序如果他们有winratio等于他们winratio的顺序。我不确定如何将两个比较器组合在一起并给它们一个层次结构,因此它知道哪种类型优先于另一个。

由于

3 个答案:

答案 0 :(得分:3)

计算winRatio中的差异,如果是0,则返回名称差异,例如......

public class MultiComparator implements Comparator<Player> {

    @Override
    public int compare(Player o1, Player o2) {
        int result = (int) (o1.getWinRatio() - o2.getWinRatio());
        if (result == 0) {
            result = o1.getUserName().compareTo(o2.getUserName());
        }
        return result;
    }

}

因为我没有什么可继续的,所以我用了这个

public interface Player {
    public String getUserName();
    public long getWinRatio();
}

作为基础对象

另一个(奇怪的)想法可能是创建一个&#34;链接&#34; Comparator,允许您带两个(或更多)Comparator并将它们链接在一起,这样当任何一个Comparator的结果为0时,它会继续尝试将值与列表中的Comparator进行比较...

public class RatioComparator implements Comparator<Player> {

    @Override
    public int compare(Player o1, Player o2) {
        return (int) (o1.getWinRatio() - o2.getWinRatio());
    }

}

public class NameComparator implements Comparator<Player> {

    @Override
    public int compare(Player o1, Player o2) {
        return o1.getUserName().compareTo(o2.getUserName());
    }

}

public class ChainedComparator implements Comparator<Player> {

    private Comparator<Player>[] comparators;

    public ChainedComparator(Comparator<Player>... comparators) {
        this.comparators = comparators;
    }

    @Override
    public int compare(Player o1, Player o2) {
        int result = -1;
        for (Comparator<Player> proxy : comparators) {
            result = proxy.compare(o1, o2);
            if (result != 0) {
                break;
            }
        }
        return result;
    }
}

你可以使用像...这样的东西。

Collections.sort(list, new ChainedComparator(new RatioComparator(), new NameComparator()));

这是未经测试的,只是一个粗略的想法;)

答案 1 :(得分:0)

使用比较方法中的以下代码

可以实现您想要的效果
int compare(T o1, T o2){
   if(o1.winratio < o2.winratio){
      return -1;
   }else if(o1.winratio < o2.winratio){
      return +1;
   }else{
     return o1.userName.compareTo(o2.userName);
   }
}

这应该可行,我建议实现Comparable接口来处理默认排序情况......

答案 2 :(得分:-1)

  

如果他们有相同的奖励,可以根据用户名进行排序

这表明您应该使用userName来实现comparable(用于自然排序)。对于winRatio,使用comparator,如果winRatio相等,也要检查他们的userName。