Java 按升序和降序排列列表的规则是什么?
我一直在试图了解使用可比排序是如何工作的。我的课堂活动实现了类似的界面。我试图理解activity.finish-this.finish是如何完成的;按降序排序以及this.finish-activity.finish如何按升序排序。我不知道在升序和降序中首先使用什么进行排序Java 按升序和降序排列列表的规则是什么?,java,sorting,comparable,Java,Sorting,Comparable,我一直在试图了解使用可比排序是如何工作的。我的课堂活动实现了类似的界面。我试图理解activity.finish-this.finish是如何完成的;按降序排序以及this.finish-activity.finish如何按升序排序。我不知道在升序和降序中首先使用什么进行排序 class Activity implements Comparable { int start; int finish; public Activity(int start, int finis
class Activity implements Comparable {
int start;
int finish;
public Activity(int start, int finish) {
this.start = start;
this.finish = finish;
}
@Override
public int compareTo(Object o) {
Activity activity = (Activity) o;
return activity.finish-this.finish;
}
}
public class ActivitySelectionProblem {
public static void main(String[] args) {
int start[] = {1, 3, 0, 5, 8, 5};
int finish[] = {2, 4, 10, 7, 9, 9};
List<Activity> list = new ArrayList<>();
for(int i = 0 ; i < start.length ; i++){
list.add(new Activity(start[i], finish[i]));
}
Collections.sort(list);
}
}
类活动实现了可比较的{
int启动;
整饰;
公共活动(整数开始、整数结束){
this.start=start;
this.finish=完成;
}
@凌驾
公共整数比较对象(对象o){
活动活动=(活动)o;
返回activity.finish-this.finish;
}
}
公共类活动选择问题{
公共静态void main(字符串[]args){
int start[]={1,3,0,5,8,5};
int finish[]={2,4,10,7,9,9};
列表=新的ArrayList();
对于(int i=0;i
它很粗糙。比较结果小于时,返回小于0
,大于时返回大于0
,等于时返回0
。代码的作用并不明显。相反,我会使用-
@Override
public int compareTo(Object o) {
return Integer.compare(this.finish, ((Activity) o).finish);
}
答案是正确的。另外,考虑使用<代码>比较器 >而不是<代码>可比针对您的情况。
tl;博士
Collections.sort(//对“列表”进行排序的实用方法。
activitiesAscending,//从原始输入列表复制的列表。
Comparator.comparingInt(Activity::finish)//为比较'int'值而构建的'Comparator'接口的预定义实现。
); // 结果将修改已通过的列表,并根据已通过的“Comparator”的逻辑进行排序。
收藏.分类(
活动下降,
Collections.reverseOrder(//反转传递的'Comparator'对象的排序逻辑。
Comparator.comparingit(Activity::finish)//与上面看到的“Comparator”相同。
)
);
比较
与相等一致
另外一个问题是,如果您阅读Javadoc for,您会发现通常最好是compareTo
的逻辑与等于
的逻辑保持恒定
但您希望仅在finish
成员字段上进行比较。因此,您应该编写您的equals
(和hashCode
),以便只关注finish
。但这意味着问题中看到的最后两个对象将被视为相等,因为它们的finish
共享值9
。我希望你不要认为这两个物体是相等的。< /P>
比较器
在类之外定义一个类可能比实现活动
类更合适。我们在这个答案的其余部分就是这么做的
使用Java16,我们可以将活动
类定义为一个类。编译器隐式地创建构造函数、getter、equals
&hashCode
和toString
。使用record
对这个答案并不重要,但会使示例代码简短
package work.basil.example;
公共记录活动(int开始、int结束)
{
}
Comparator.comparingit
我们可以使用
我们使用双冒号字符来命名从比较对象检索int时应该使用的方法。该方法引用是Activity::finish
。在记录中,默认的getter方法与属性名命名相同,没有常见的JavaBeans前缀get
。因此,只需将finish
作为方法名,而不是getFinish
Comparator.comparingInt(Activity::finish))//将从'Activity'传递到'Comparator'的方法引用构建为比较'int'值。
让我们使用方便的语法定义输入
列表活动=
名单(
新活动(1,2),
新活动(3,4),
新活动(0,10),
新活动(5,7),
新活动(8,9),
新活动(5、9)
);
该代码生成的列表为。我们想对列表进行排序,因此需要一个可修改的列表。将该不可修改列表馈送给list
的可修改实现的构造函数,例如
ListactivitiesAscending=newarraylist(activities);
使用实用程序方法Collections.sort
对新列表进行排序。如我们前面所示,传递一个比较器
Collections.sort(activitiesAscending、Comparator.comparingInt(Activity::finish));
相反,按照降序排列,首先是9
完成对象,最后是2
完成对象,我们再次调用集合。排序
。但是我们传递一个不同的比较器。我们将原始的comparingit
比较器传递给实用方法Collections.reverseOrder
,以生成一个新的比较器
ListactivitiesDescending=newarraylist(活动);
排序(activitiesDescending、Collections.reverseOrder(Comparator.comparingInt(Activity::finish));
完整的代码示例
列表活动=
名单(
新活动(1,2),
新活动(3)