我是stackoverflow.com上的新手,但每当我遇到问题时,我经常用它来搜索答案,但现在我找不到任何搜索我的问题的结果所以我在这里问:) 我正在攻读OCPJP SE 7认证,考试1Z0-804,我正在使用一本书(只有一本可用的,Ganesh \ Sharma的一本) 在集合章节中,关于Comparator接口,本书提供了使用Comparator和Comparable接口对Student元素数组进行排序的示例,但问题是关于Comparator:
import java.util.*;
class Student implements Comparable<Student> {
private String id, name;
private Double cgpa;
public String getName() {
return name;
}
public String getId() {
return id;
}
public Double getCgpa() {
return cgpa;
}
public Student(String studentId, String studentName, double studentCGPA) {
id=studentId;
name=studentName;
cgpa=studentCGPA;
}
public String toString() {
return id+" "+name+" "+cgpa;
}
public int compareTo(Student that) {
return this.id.compareTo(that.id);
}
}
class StudentCGPA implements Comparator<Student> {
public int compare(Student s1, Student s2) {
return s1.getCgpa().compareTo(s2.getCgpa());
}
}
class MyMainClass {
public static void main(String[] args) {
Student[] students = { new Student("cs011", "Lennon", 3.1),
new Student("cs021", "McCartney", 3.4),
new Student("cs012", "Harrison", 2.7),
new Student("cs022", "Starr", 3.7),
};
Arrays.sort(students, new StudentCGPA());
System.out.println(Arrays.toString(students));
}
}
所以它创建了一个新类只用于将Comparator接口与两个Student对象一起使用,但我认为这非常不舒服所以我想知道:为什么我不能使用嵌套类(在Student中)?像这样:
import java.util.*;
class Student implements Comparable<Student> {
private String id, name;
private Double cgpa;
public String getName() {
return name;
}
public String getId() {
return id;
}
public Double getCgpa() {
return cgpa;
}
public Student(String studentId, String studentName, double studentCGPA) {
id=studentId;
name=studentName;
cgpa=studentCGPA;
}
public String toString() {
return id+" "+name+" "+cgpa;
}
public int compareTo(Student that) {
return this.id.compareTo(that.id);
}
static class StudentCGPA implements Comparator<Student> {
public int compare(Student s1, Student s2) {
return s1.getCgpa().compareTo(s2.getCgpa());
}
}
}
class MyMainClass {
public static void main(String[] args) {
Student[] students = { new Student("cs011", "Lennon", 3.1),
new Student("cs021", "McCartney", 3.4),
new Student("cs012", "Harrison", 2.7),
new Student("cs022", "Starr", 3.7),
};
Arrays.sort(students, new Student.StudentCGPA());
System.out.println(Arrays.toString(students));
}
}
这本书没有提到使用嵌套类而不是普通类,但我不明白为什么这样做会不好...我的代码(第二个)有什么问题吗?我是否应该遵循本书所说的内容,因为我对比较器的实现是错误的? (注意:代码编译并运行没有问题,在两种情况下都有预期的输出)
[cs012 Harrison 2.7, cs011 Lennon 3.1, cs021 McCartney 3.4, cs022 Starr 3.7]
请帮助:D提前致谢。
答案 0 :(得分:4)
您可以将Comparator
实现为被比较的静态嵌套类, if 您可以控制该类(如果它是类而不是接口) 。但是,根据目标类本身不支持的顺序(无论是通过Comparable
还是通过提供{},您想要比较您无法控制的类的实例并不罕见。 {1}}类)。在这种情况下,您必须创建自己的Comparator
。
即使您控制了所有内容,是否将Comparator
实现为顶级类也是一种品味问题。我不确定你为什么称之为“不舒服”;我自己,我通常喜欢尽可能避免使用嵌套类。另请注意,无论是否嵌套,Comparator
实现类都将编译为单独的类文件。
答案 1 :(得分:-2)
您没有理由不实际实施 Comparable
和Comparator
class Student implements Comparable<Student>, Comparator<Student> {
private final String id;
private final String name;
private final Double cgpa;
public String getName() {
return name;
}
public String getId() {
return id;
}
public Double getCgpa() {
return cgpa;
}
public Student(String studentId, String studentName, double studentCGPA) {
id = studentId;
name = studentName;
cgpa = studentCGPA;
}
@Override
public String toString() {
return id + " " + name + " " + cgpa;
}
@Override
public int compareTo(Student that) {
return this.id.compareTo(that.id);
}
@Override
public int compare(Student o1, Student o2) {
return o1.getCgpa().compareTo(o2.getCgpa());
}
}
然而,通常更合适的是仅实现Comparable
并使用其他方法(例如内部类或匿名类)来选择不同的订单。
class ByCgpa implements Comparator<Student> {
@Override
public int compare(Student o1, Student o2) {
return o1.getCgpa().compareTo(o2.getCgpa());
}
}
Collections.sort(list, new ByCgpa());
static void sortByCgpaAndName(Collection<Student> students) {
Collections.sort(students, new Comparator<Student> () {
@Override
public int compare(Student o1, Student o2) {
int byCgpa = o1.getCgpa().compareTo(o2.getCgpa());
return byCgpa != 0 ? byCgpa : o1.name.compareTo(o2.name);
}
});
}
有关进一步的讨论,请参阅here。