Spring 系列目錄(http://www.javashuo.com/article/p-kqecupyl-bm.html)html
Integer 內部實現了 Comparable 接口java
public final class Integer extends Number implements Comparable<Integer> { public int compareTo(Integer anotherInteger) { return compare(this.value, anotherInteger.value); } public static int compare(int x, int y) { return (x < y) ? -1 : ((x == y) ? 0 : 1); } }
這樣就能夠用集合或數組工具進行排序,不須要再定義比較器了。spring
@Test public void test() { // 1. 集合排序 List<Integer> integerList = Arrays.asList(3, 2, 1, 5, 6); // integerList.sort() Collections.sort(integerList); Assert.assertEquals(Arrays.asList(1, 2, 3, 5, 6), integerList); // 2. 數組排序 Arrays.sort(new Integer[]{3, 2, 1, 5, 6}); }
還在另一種狀況,須要排序的對象沒有實現 Comparable,那怎麼辦呢?JDK 提供了一個專門的比較器 Comparator。數組
@FunctionalInterface public interface Comparator<T> { // o1>o2: 1; o1=o2: 0;o1<o2: -1; // Assert.assertEquals(-1, Integer.compare(1, 2)); int compare(T o1, T o2); }
Collections 集合對應的排序方式以下:ide
public static <T> void sort(List<T> list, Comparator<? super T> c) { list.sort(c); }
在 Spring 中提供了接口和註解兩種方式,注意 Spring 中數值越小級別越高,位於 core 包中:工具
一是實現 Ordered 或 PriorityOrdered 接口,PriorityOrdered 的級別要優先於 Ordered,使用 OrderComparator 比較器。測試
二是使用 @Order(Spring 規範) 或 @Priority(JDK 規範) 註解,使用 AnnotationAwareOrderComparator 比較器。this
public interface PriorityOrdered extends Ordered { } public interface Ordered { int HIGHEST_PRECEDENCE = Integer.MIN_VALUE; int LOWEST_PRECEDENCE = Integer.MAX_VALUE; int getOrder(); }
// 實現 JDK 的 Comparator public class OrderComparator implements Comparator<Object> { @Override public int compare(@Nullable Object o1, @Nullable Object o2) { return doCompare(o1, o2, null); } private int doCompare(@Nullable Object o1, @Nullable Object o2, @Nullable OrderSourceProvider sourceProvider) { boolean p1 = (o1 instanceof PriorityOrdered); boolean p2 = (o2 instanceof PriorityOrdered); // 1. PriorityOrdered 接口優先 if (p1 && !p2) { return -1; } else if (p2 && !p1) { return 1; } // 2. 比較 getOrder 的值,數值越小越優先 int i1 = getOrder(o1, sourceProvider); int i2 = getOrder(o2, sourceProvider); return Integer.compare(i1, i2); } }
使用和 JDK 一致。code
AnnotationAwareOrderComparator 繼承自 OrderComparator 增長了 @Order(Spring 規範) 或 @Priority(JDK 規範) 註解的處理。htm
public @interface Order { int value() default Ordered.LOWEST_PRECEDENCE; } // javax.annotation.Priority public @interface Priority { int value(); }
AnnotationAwareOrderComparator 重寫了 findOrder,增長了對 @Order 或 @Priority 兩個註解的處理。使用 OrderUtils 工具類。
@Override protected Integer findOrder(Object obj) { // Check for regular Ordered interface Integer order = super.findOrder(obj); if (order != null) { return order; } // Check for @Order and @Priority on various kinds of elements if (obj instanceof Class) { return OrderUtils.getOrder((Class<?>) obj); } else if (obj instanceof Method) { Order ann = AnnotationUtils.findAnnotation((Method) obj, Order.class); if (ann != null) { return ann.value(); } } else if (obj instanceof AnnotatedElement) { Order ann = AnnotationUtils.getAnnotation((AnnotatedElement) obj, Order.class); if (ann != null) { return ann.value(); } } else { order = OrderUtils.getOrder(obj.getClass()); if (order == null && obj instanceof DecoratingProxy) { order = OrderUtils.getOrder(((DecoratingProxy) obj).getDecoratedClass()); } } return order; }
有如下 4 個類,分別是實現 PriorityOrdered 接口、實現 Ordered 接口、@Order 註解、普通 bean.
class A implements PriorityOrdered { @Override public int getOrder() { return Ordered.LOWEST_PRECEDENCE; } } class B implements Ordered { @Override public int getOrder() { return 10; } } @Order(0) class C { } class D { }
測試排序的結果:
@Test public void test() { List<Object> list = Arrays.asList(new D(), new C(), new B(), new A()); AnnotationAwareOrderComparator.sort(list); // A C B D list.forEach(o -> System.out.print(o.getClass().getSimpleName() + " ")); }
A 實現了 PriorityOrdered 接口排第一位、B 和 C 分別比較 order 值、D 排最後。
天天用心記錄一點點。內容也許不重要,但習慣很重要!