我对有效使用Java比较器有疑问。
class MyClass {
//Active State: OPEN, PENDING, RUNNING
private String state;
private Date startDate;
private Date endDate;
}
在此,state
字段的可能值为OPEN,PENDING,RUNNING,CLOSED,CANCELED等,其中OPEN,PENDING和RUNNING为活动状态。现在,我想编写对进行排序的比较器List<MyClass>
,以使活动对象排在最前面,startDate
然后由排序,然后是基于进行排序的非活动对象endDate
。
static final Set<String> ACTIVE;// this set contains OPEN, PENDING, RUNNING
List<MyClass> myList;//This is my list
...
Collections.sort(myList, new Comparator<MyClass>() {
@Override
public int compare(MyClass o1, MyClass o2) {
int c;
boolean isO2 = ACTIVE.contains(o2.getState());
boolean isO1 = ACTIVE.contains(o1.getState());
if (isO2 && isO1) {
c = DateTimeComparator.getInstance().compare(o2.getStartDate(), o1.getStartDate());
} else if (isO2) {
c = 1;
} else if (isO1) {
c = -1;
} else {
c = DateTimeComparator.getInstance().compare(o2.getEndDate(), o1.getEndDate());
}
return c;
}
});
我的问题是我上面拥有单个比较器的实现是否良好?还是有更好的方法来做到这一点?我很可能必须坚持使用Java 7,但是也欢迎使用Java 8的解决方案。
在Java 8中,我认为使用Comparator :: comparing会更干净一些。例如:
Comparator<MyClass> comparator = Comparator.nullsFirst(Comparator.comparing((MyClass myClass) -> !isActive(myClass))
.thenComparing((MyClass myClass) -> isActive(myClass) ? myClass.startDate : myClass.endDate, Comparator.nullsFirst(DateTimeComparator.getInstance())));
private static boolean isActive(MyClass myClass)
{
switch (myClass.state)
{
case "OPEN":
case "PENDING":
case "RUNNING":
return true;
default:
return false;
}
}
在Java 7中,假设类路径上有Guava,则可以使用Ordering。例如:
Comparator<MyClass> comparator = Ordering.natural().reverse().onResultOf(new Function<MyClass, Boolean>() {
@Override
public Boolean apply(MyClass myClass) {
return isActive(myClass);
}
})
.compound(Ordering.from(DateTimeComparator.getInstance()).nullsFirst().onResultOf(new Function<MyClass, Date>() {
@Override
public Date apply(MyClass myClass) {
return isActive(myClass) ? myClass.startDate : myClass.endDate;
}
}))
.nullsFirst();
本文收集自互联网,转载请注明来源。
如有侵权,请联系 [email protected] 删除。
我来说两句