重写抽象方法compare()。

4

你好,我是一个相对新手的程序员,我在比较方法方面遇到了困难。我有几个类,我的初始问题出现在我的父类中。

我收到了这个错误:

Person不是抽象的,并且没有在Comparator中重写compare(java.lang.Object, java.lang.Object)方法

    public class Person implements Comparator
    {
     //some methods

    public int compare(Person p1, Person p2)
    {
       // if last names are the same compare first names
       if(p1.getLastName().equals(p2.getLastName()))
       {
           return p1.getFirstName().compareTo(p2.getFirstName());
       }
       return p1.getLastName().compareTo(p2.getLastName());

    }

我的子类看起来像这样:

    public class Player extends Person implements Comparator
    {
      //some methods

    public int compare(Player p1, Player p2)
    {
       if(p1.getGamesPlayed()<p2.getGamesPlayed())

       {
          return -1;
       }else if (p1.getGamesPlayed()==p2.getGamesPlayed())
       {
          return 0;
       }else
       {
          return 1;
       }
     }

我也有一个俱乐部类,它将所有信息存储在ArrayList<Player>团队中。

我的接口:

    public interface Comparator<T>
    {
        int compare(T o1, T o2);
    }

我也有这个类

   public class ComparePlayers implements Comparator<Player>
   {

      public int compare(Player p1, Player p2)
      {
         if(p1.getGamesPlayed()< p2.getGamesPlayed())
         {
            return -1;
         }else if(p1.getGamesPlayed()== p2.getGamesPlayed())
         {
            return p1.getLastName().compareTo(p2.getLastName());
         }else
         {
             return 1;
         }
       }

这个的规范如下:
当签约新球员时,应按姓氏字母顺序(如果姓氏相同,则按名字顺序)将其插入到俱乐部类中。为此,请使您的人物和球员类实现适当的Comparable接口。
编写一个实现Comparator接口的ComparePlayers类。它应该通过已玩游戏的数量(如果已玩游戏的数量相同,则按姓氏字母顺序)比较球员。为Club类实现一个接受Comparator参数的新构造函数。因此,请编写一个主程序,以已玩游戏的减少顺序列出俱乐部中每个球员的信息。这应该允许由主程序指定排序方式,而无需修改其他任何类的代码。
如果这段话描述冗长,很抱歉,但我不知道哪里出了问题,我尝试了几种变化,但无济于事。这项任务要在星期五前完成,希望您能给我一些指引。

3
不要自己编写Comparator接口,而应使用java.util包中的接口。 - karakuricoder
4个回答

9

将您的比较实现更改为:

public int compare(Object o1, Object 02)
{
   Person p1 = (Person)o1;
   Person p2 = (Person)o2;
   // if last names are the same compare first names
   if(p1.getLastName().equals(p2.getLastName()))
   {
       return p1.getFirstName().compareTo(p2.getFirstName());
   }
   return p1.getLastName().compareTo(p2.getLastName());

}

1
谢谢,我总是错过眼前的东西 :) - Cjb1982
3
建议使用范型进行编译时类型检查,就像原帖中使用的 Comparator<Player> 一样。 - Hovercraft Full Of Eels
@Hovercraft:我认为其他答案已经涵盖了那个选项。我的方法只是修复问题中特定的错误的一种方式 :) - Mark Pope
@Cjb1982:明白了,对我的错误假设表示抱歉。但更重要的是,你是否理解我们关于泛型使用的讨论以及为什么它很重要? - Hovercraft Full Of Eels
@Hovercraft:别担心: )。是的,我明白“通用”的意思。感谢您的帮助。 - Cjb1982

4

PersonPlayer不应该实现Comparator接口。如果它们需要按某种自然顺序进行比较,那么应该实现Comparable接口。

你的ComparePlayers类看起来没问题,有什么问题吗?(我假设你在这里使用了java.util.Comparator,是吗?)

为了对列表进行排序,你可以使用Collections.sort(players, new ComparePlayers());,其中players的类型是List<Player>(或者是该接口的实现)。

请注意,如果PersonPlayer应该是Comparable的,那么你需要实现compareTo(Person p2)compareTo(Player p2)方法,其中Player的实现应该对于平局时调用super.compareTo(p2);

示例:

class Person<T extends Person> implements Comparable<T> {
  public int compareTo(Tp2) { ... }
}

class Player extends Person<Player> {
  public int compareTo(Player p2) {
    ...
    if(gamesPlayed == p2.getGamesPlayed() ) {
      return super.compareTo(p2);
    }
    ...
  }
}

这会给我一个编译错误。无法使用不同的参数继承Comparable:<Player>和<Person>。 - Cjb1982

1
Comparator的compare方法接受两个Object参数,而你的方法接受两个Person参数,因此编译器无法找到你重写该方法的位置。解决方案是将方法的参数更改为Objects,或者(最好)使用通用的Comparator,因为这将允许你的compare方法具有Person参数,并且在编译时添加类型安全检查。
编辑1:糟糕,你已经有一个通用的Comparable类的示例了。
编辑2:我没有看到你正在创建自己的接口,直到我读到关于这一点的评论。我同意评论者的观点-使用java.util中已经存在的类。

0

就像异常所提示的,此声明

  • public int compare(Person p1, Person p2)

必须更改为

  • public int compare(Object p1, Object p2)

然后您还需要调整方法代码,以便它能够正常工作。

public int compare(Object p1, Object p2)
{
   // if last names are the same compare first names
   if(((Person)p1).getLastName().equals(((Person)p2).getLastName()))
   {
       return ((Person)p1).getFirstName().compareTo(((Person)p2).getFirstName());
   }
   return ((Person)p1).getLastName().compareTo(((Person)p2).getLastName());

}

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接