Java 在末尾使用一个元素进行排序

Java 在末尾使用一个元素进行排序,java,sorting,java-8,java-stream,Java,Sorting,Java 8,Java Stream,我有一个对象列表,我想按属性的字母顺序对其排序。但如果该属性与特定字符串匹配,我想添加一个异常规则。例如: public class Car { String name; } 一种可能的方法是将分区用作: Map<Boolean, List<Car>> partitionedCars = cars .stream() .collect(Collectors.partitioningBy(a -> a.getName().equa

我有一个对象列表,我想按属性的字母顺序对其排序。但如果该属性与特定字符串匹配,我想添加一个异常规则。例如:

public class Car {
  String name;
}

一种可能的方法是将分区用作:

Map<Boolean, List<Car>> partitionedCars = cars
        .stream()
        .collect(Collectors.partitioningBy(a -> a.getName().equals("Unassigned")));

List<Car> sortedCars = Stream.concat(partitionedCars.get(Boolean.FALSE).stream()
        .sorted(Comparator.comparing(Car::getName)), partitionedCars.get(Boolean.TRUE).stream())
        .collect(Collectors.toList());
Map partitionedCars=cars
.stream()
.collect(collector.partitionby(a->a.getName().equals(“Unassigned”));
List sortedCars=Stream.concat(partitionedCars.get(Boolean.FALSE).Stream()
.sorted(Comparator.comparing(Car::getName)),partitionedCars.get(Boolean.TRUE).stream()
.collect(Collectors.toList());
列出分拣车=车辆
.stream()
.sorted(Comparator.comparating(
车::getName,
比较器。比较((字符串x)->x.equals(“未赋值”))
.Then比较(Comparator.naturalOrder()))
.collect(Collectors.toList());
这里发生了很多事情。首先我使用的是比较器。比较(函数,比较器);然后是
(字符串x)->x.equals(“未赋值”)
,它实际比较
布尔值(即
可比较的
);然后使用
(String x)
这一事实-因为此类型见证用于正确推断类型

您可以在比较器中将“Unassigned”替换为字母表字符串的末尾

Comparator.comparing(car -> car.getName().equals("Unassigned") ? "ZZZ" : car.getName())

最直接和易于阅读的解决方案可能是编写一个实现排序逻辑的自定义比较器

您仍然可以使用
比较器。比较
方法可以使它更漂亮一些,不过:

public static final String UNASSIGNED = "Unassigned";

List<Car> cars = List.of(
    new Car("Unassigned"), 
    new Car("Nissan"), 
    new Car("Yamaha"), 
    new Car("Honda"));

List<Car> sortedCars = cars.stream()
    .sorted(Comparator.comparing(Car::getName, (name1, name2) -> {
            if (name1.equals(name2)) return 0;
            if (name1.equals(UNASSIGNED)) return 1;
            if (name2.equals(UNASSIGNED)) return -1;
            return name1.compareTo(name2);
    }))
    .collect(toList());

或者,只需删除“Unassigned”的所有实例,然后在
列表的末尾添加多个实例。例如:

int numberOfUnassigned = 0;
for (Iterator<Car> iterator = sortedCars.iterator(); iterator.hasNext();) {
    String str = iterator.next().getName();
    if (str.equals("Unassigned")) {
        iterator.remove();
        numberOfUnassigned++;
    }
}
int numberOfUnassigned=0;
for(Iterator Iterator=sortedCars.Iterator();Iterator.hasNext();){
String str=iterator.next().getName();
如果(str.equals(“Unassigned”)){
iterator.remove();
numberOfUnassigned++;
}
}

然后在末尾添加
numberOfUnassigned
的编号。

这是一种巧妙的方法,但会浪费资源。。。当然,聪明!但是我认为,
比较((字符串x)->x.equals(“未赋值”)
的技巧非常棘手,它需要在代码中给出解释性的注释,它将在生产中使用…@Lii,这是留给读者的练习。。。我提到它对一个
布尔值
(即
可比较的
)进行排序,这应该提供正确的方向。真聪明。
Comparator.comparing(car -> car.getName().equals("Unassigned") ? "ZZZ" : car.getName())
public static final String UNASSIGNED = "Unassigned";

List<Car> cars = List.of(
    new Car("Unassigned"), 
    new Car("Nissan"), 
    new Car("Yamaha"), 
    new Car("Honda"));

List<Car> sortedCars = cars.stream()
    .sorted(Comparator.comparing(Car::getName, (name1, name2) -> {
            if (name1.equals(name2)) return 0;
            if (name1.equals(UNASSIGNED)) return 1;
            if (name2.equals(UNASSIGNED)) return -1;
            return name1.compareTo(name2);
    }))
    .collect(toList());
List<Car> sortedCars = cars.stream()
    .sorted(Comparator.comparing(Car::getName, withValueAtEnd(UNASSIGNED)))
    .collect(toList());

public static <T extends Comparable<T>> Comparator<T> withValueAtEnd(T atEnd) {
  return withValueAtEnd(atEnd, Comparator.naturalOrder());
}

public static <T> Comparator<T> withValueAtEnd(T atEnd, Comparator<T> c) {
    return (a, b) -> {
        if (a.equals(atEnd)) return 1;
        if (b.equals(atEnd)) return -1;
        return c.compare(a, b);
    };
}
cars.sort(UNASSIGNED_COMPARATOR);
int numberOfUnassigned = 0;
for (Iterator<Car> iterator = sortedCars.iterator(); iterator.hasNext();) {
    String str = iterator.next().getName();
    if (str.equals("Unassigned")) {
        iterator.remove();
        numberOfUnassigned++;
    }
}