2015-10-08 35 views
3

給定一個類。在Java中使用流暢的鏈接排序集合8

public class Entity { 

    private Long id; 
    private String prodName; 
    private BigDecimal price; 

    // Constructors + getters + setters + hashcode() + equals() + toString(). 
} 

構建一個列表Entity

List<Entity> list = new ArrayList<>(); 

Entity entity = new Entity(); 
entity.setId(1L); 
entity.setProdName("A"); 
entity.setPrice(new BigDecimal(10)); 
list.add(entity); 

entity = new Entity(); 
entity.setId(2L); 
entity.setProdName("B"); 
entity.setPrice(new BigDecimal(20)); 
list.add(entity); 

entity = new Entity(); 
entity.setId(3L); 
entity.setProdName("C"); 
entity.setPrice(new BigDecimal(30)); 
list.add(entity); 

entity = new Entity(); 
entity.setId(4L); 
entity.setProdName("D"); 
entity.setPrice(new BigDecimal(40)); 
list.add(entity); 

entity = new Entity(); 
entity.setId(5L); 
entity.setProdName("E"); 
entity.setPrice(new BigDecimal(50)); 
list.add(entity); 

entity = new Entity(); 
entity.setId(6L); 
entity.setProdName("F"); 
entity.setPrice(new BigDecimal(60)); 
list.add(entity); 

entity = new Entity(); 
entity.setId(7L); 
entity.setProdName("F"); 
entity.setPrice(new BigDecimal(60)); 
list.add(entity); 

試圖名單由priceprodName降序通過id進行排序,然後按升序排列。

Comparator<Entity> comparator = Comparator.comparing(Entity::getPrice).reversed(); 
comparator = comparator.thenComparing(Entity::getProdName).reversed(); 
comparator = comparator.thenComparingLong(Entity::getId); 

list = list.stream().sorted(comparator).collect(Collectors.toList()); 
// Or Collections.sort(list, comparator); 
list.stream().forEachOrdered(l -> System.out.println(l.getId() + " : " + l.getPrice() + " : " + l.getProdName())); 

執行排序後,列表應該如下所示。

6 : 60 : F 
7 : 60 : F 
5 : 50 : E 
4 : 40 : D 
3 : 30 : C 
2 : 20 : B 
1 : 10 : A 

不過這個名單,進行整理後,顯示如下。

1 : 10 : A 
2 : 20 : B 
3 : 30 : C 
4 : 40 : D 
5 : 50 : E 
6 : 60 : F 
7 : 60 : F 

排序後的列表是不根據給定的準則(由idpriceprodName和升序降序)。

還需要做些什麼?

+0

嘗試根據本文提供的示例嘗試一些代碼:http://www.leveluplunch.com/java/tutorials/007-sort-arraylist-stream-of -objects-in-java8/ –

+0

'comparator.thenComparingLong(Entity :: getId).reversed()'? – marstran

+0

[這裏](http://stackoverflow.com/questions/14154127/collections-sortlistt-comparator-super-t-method-example)是用於收集排序使用比較一個很好的例子。 – mystery

回答

5

你每次調用逆轉時間()扭轉整個比較。相反,請按照您的描述說明:

Comparator<Entity> comparator = Comparator.comparing(Entity::getPrice, 
                Comparator.reverseOrder()); 
comparator = comparator.thenComparing(Entity::getProdName, 
             Comparator.reverseOrder()); 
comparator = comparator.thenComparingLong(Entity::getId); 

list = list.stream().sorted(comparator).collect(Collectors.toList()); 
list.stream().forEachOrdered(l -> System.out.println(l.getId() + " : " + l.getPrice() + " : " + l.getProdName())); 
+4

當然,程序員誰意識到'逆轉()'適用於整個比較器可以簡單地使用'Comparator.comparing(Entity :: getPrice).thenComparing(Entity :: getProdName).reversed().thenComparingLong(Entity :: getId)''實現相同... – Holger

4

考慮您的代碼註釋:

Comparator<Entity> comparator = Comparator.comparing(Entity::getPrice).reversed(); // compare by descending price 
comparator = comparator.thenComparing(Entity::getProdName) // then compare by ascending name 
         .reversed(); // then reverse this order: so you now sort by ascending price and descending name 
comparator = comparator.thenComparingLong(Entity::getId); // and finally compare by ascending id 

所以最後比較的是:價格上升,下降的名字,那麼上升的ID,這正是你作爲結果。

所以,錯誤是你鏈接到正確的reversed()來電。

下面的工作:

Comparator<Entity> comparator = Comparator.comparing(Entity::getPrice).reversed(); //sort by descending price 
comparator = comparator.thenComparing(Comparator.comparing(Entity::getProdName).reversed()); // then sort by descending name 
comparator = comparator.thenComparingLong(Entity::getId); // then sort by ascending id