繁体   English   中英

什么决定了 Comparator / Comparable 集合类中的升序或降序?

[英]What determines ascending or descending order in Comparator / Comparable collection class?

我知道我们可以根据我们的要求对存储在 Collection 中的对象进行排序或排序。

虽然我得到了深刻的理解,但我不相信这样的事实,即升序和降序排列是通过 (a - b) -> 升序或 (b - a) -> 降序实现的,其中 "a" 和 "b" 是类我们选择比较的成员。

例子:

public int compareTo(Student s) {
     return this.grade - s.grade; //ascending order 
    // return s.grade - this.grade; // descending order
}

排序对象元素背后的逻辑是什么? "(this.grade - s.grade)" 如果正 1 将 "this.grade" 移到前面并按顺序放置 "s.grade",为什么不反过来呢? 谁验证比较结果(+1,-1,0),然后分别按升序或降序排列,有没有描述这部分内部工作的文档?

public class Student implements Comparable <Student>{
    String name;
    int grade;
    public Student(String name, int grade) {
        this.name = name;
        this.grade = grade;
    }
    public int compareTo(Student s) {
         return this.grade - s.grade; //ascending order 
        // return s.grade - this.grade; // descending order
    }
    public String toString() {
        return this.name + ", " + this.grade;
    }
}

请分享,非常感谢!


编辑:

我得到了 Java 文档,我的问题是:

sort these grades (13, 2)

Case ascending -> return this.grade - s.grade;

picture in my mind: 
compare (13, 2) , (13 - 2) > 0 so move 2 to front.
result -> 2, 13
------
Case descending -> return s.grade - this.grade;

picture in my mind: 
compare (2, 13) , (2 - 13) < 0 so move 13 to front.

result -> 13, 2

“这是怎么回事?” 是我原来的问题。 我阅读了文档,仍然无法弄清楚。

排序对象元素背后的逻辑是什么? "(this.grade - s.grade)" 如果正 1 将 "this.grade" 移到前面并按顺序放置 "s.grade",为什么不反过来呢?

用负数表示“这小于那个”,用正数表示“这大于那个”,用 0 表示“这两件事相等”已经在许多计算机语言中使用了 30 多年。

谁验证比较结果(+1、-1、0),然后分别按升序/降序排列,是否有描述这部分内部工作的文档?

有几个内部类使用返回值对数组或集合中的元素进行重新排序,包括

Collections.sort() Arrays.sort() TreeSet

编辑

要回答它是如何工作的,您必须查看我上面列出的每个类的源代码。 其中一些非常复杂,试图使排序尽可能高效。 但总的来说,这一切都归结为这样的代码:

if( data[i].compareTo(data[j]) > 0 ){
   // swap data[i] and  data[j]
}

@DavidPrun 好问题。 我试过用一个例子来解释这一点。

(x,y) -> (2, 5)

升序(x.compareTo(y)):

if x.compareTo(y) == 1, then x > y , since y is smaller than x, you would have to move y in front of x.

2.compareTo(5) == 1 , Then don't move 5 in front of 2.

降序(y.compareTo(x)):

if y.compareTo(x) == 1, then y > x , since y is greater than x, you would have to move y in front of x.

5.compareTo(2) == -1 , Move 5 in front of 2.

基本上,如果 compareTo 方法的结果为 1,我们将始终将 y 移动到 x 之前。

Collections.sort()方法确实如此。

在 java 的sort函数中,函数compareTo(Comparable other)被调用以确定您的可比较对象与其他可比较对象的比较方式。

假设我有一个圆,我想按直径进行比较

public class Circle implements Comparable<Cricle> {
 int diameter;
 //constructor
 public int compareTo(Circle c){
  return this.diameter-c.diameter;
   }

现在让我们制作一个圆圈数组:

ArrayList<Circle> collection = new ArrayList;
collection.add(new Circle(10)); // and more circles

现在让我们假设这是在 Collection.sort() 中定义的排序算法:

  Comparable tmp;
  for(int i=0;i<collection.size();i++){
   for(int j=i;j<collection.size();j++){
    if(collection.get(j).compareTo(collection.get(i)>0){
      //swap
      tmp=collection.get(i);
      collection.set(i,collection.get(j));
      collection.set(j,tmp);
     }
    }
   }
  

Java 当然不使用冒泡排序,但这是一个粗略的例子,说明您的compareTo实现将如何决定排序。

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM