Guava:Ordering 排序工具

这篇具有很好参考价值的文章主要介绍了Guava:Ordering 排序工具。希望对大家有所帮助。如果存在错误或未考虑完全的地方,请大家不吝赐教,您也可以点击"举报违法"按钮提交疑问。

简介

排序器 Ordering 是 Guava流畅风格比较器 Comparator 的实现,它可以用来为构建复杂的比较器,以完成集合排序的功能。

从实现上说,Ordering 实例就是一个特殊的 Comparator 实例。Ordering 把很多基于 Comparator 的静态方法(如 Collections.max)包装为自己的实例方法(非静态方法),并且提供了链式调用方法,来定制和增强现有的比较器。

类方法说明

官方文档:Source code文章来源地址https://www.toymoban.com/news/detail-791182.html

方法名称 方法描述
allEqual()  返回一个Ordering,所有值的排序地位都是平等的,表明无排序。 将此排序传递给任何稳定排序算法都不会导致元素顺序发生变化。
arbitrary()  返回所有对象的任意顺序,即compare(a, b) == 0 就是 a == b (identity equality)。 本身的排序是没有任何含义,但是在VM的生命周期是一个常量。
binarySearch(List<? extends T> sortedList, T key)  已过时,请使用 Collections.binarySearch(List, Object, Comparator).
compare(T left, T right)  比较两个参数的顺序。
compound(Comparator<? super U> secondaryComparator)  返回一个Ordering,传入比较器作为第二排序元素。
compound(Iterable<? extends Comparator<? super T>> comparators)  返回一个Ordering,会根据传入比较器集合一次比较,直到找到一个非零的结果。
explicit(List<T> valuesInOrder)  返回一个Ordering,根据他们出现在给定的列表的顺序比较对象
explicit(T leastValue, T... remainingValuesInOrder)  返回一个Ordering,比较对象根据它们的传入的顺序。
from(Comparator<T> comparator) 
返回一个传入comparator实例的Ordering。
from(Ordering<T> ordering)  已过时。 不需要使用它
greatestOf(Iterable<E> iterable, int k)  根据Ordering对传入iterable由大到小排序,返回前K位的集合。
greatestOf(Iterator<E> iterator, int k)  根据Ordering对传入iterable由大到小排序,返回前K位的集合。
immutableSortedCopy(Iterable<E> elements)  返回一个不可变的集合,包含根据Ordering对传入元素排序后的所有元素。
isOrdered(Iterable<? extends T> iterable)  根据Ordering对传入iterable元素迭代,如果下一个元素大于或等于上一个元素,返回true。
isStrictlyOrdered(Iterable<? extends T> iterable)  根据Ordering对传入iterable元素迭代,如果下一个元素严格大于上一个元素,返回true。
leastOf(Iterable<E> iterable, int k)  根据Ordering对传入iterable由小到大排序,返回前K位的集合。
leastOf(Iterator<E> iterator, int k)  根据Ordering对传入iterable由小到大排序,返回前K位的集合。
lexicographical()  返回一个新的Ordering,通过相应的元素两两迭代,直到找到一个非零的结果。强加“字典顺序”。
max(E a, E b)  根据Ordering返回传入参数的最大值。
max(E a, E b, E c, E... rest)  根据Ordering返回传入参数的最大值。
max(Iterable<E> iterable)  根据Ordering返回传入参数的最大值。
max(Iterator<E> iterator)  根据Ordering返回传入参数的最大值。
min(E a, E b)  根据Ordering返回传入参数的最小值。
min(E a, E b, E c, E... rest)  根据Ordering返回传入参数的最小值。
min(Iterable<E> iterable)  根据Ordering返回传入参数的最小值。
min(Iterator<E> iterator)  根据Ordering返回传入参数的最小值。
natural()  对可排序类型做自然排序,如数字按大小,日期按先后排序
nullsFirst()  根据Ordering排序,null值放在最前面,并使用它来比较非空值。
nullsLast()  根据Ordering排序,null值放在最后面,并使用此排序来比较非空值。
onResultOf(Function<F,? extends T> function)  将传入function应用到每个元素上面,再通过Ordering进行排序。
<S extends T>Ordering<S> reverse() 
返回与当前Ordering相反的排序。相当于 Collections.reverseOrder(Comparator)
<E extends T> List<E> sortedCopy(Iterable<E> elements) 
返回一个可变的集合,包含根据Ordering对传入元素排序后的所有元素。
usingToString()  根据toString返回的字符串按照字典顺序排序。

 使用Demo

import com.google.common.base.Function;
import com.google.common.collect.ImmutableList;
import com.google.common.collect.Iterators;
import com.google.common.collect.Lists;
import com.google.common.collect.Ordering;
import com.google.common.primitives.Doubles;
import junit.framework.TestCase;
import org.checkerframework.checker.nullness.qual.Nullable;
import java.util.*;
import static java.util.Arrays.asList;

/**
 * 排序
 */
public class OrderingTests extends TestCase {

    /**
     * 1、allEqual 允许有null
     */
    public void testAllEqual() {
        Ordering<Object> comparator = Ordering.allEqual();
        System.out.println(comparator.equals(comparator.reverse()));

        assertEquals(0, comparator.compare(null, null));
        assertEquals(0, comparator.compare(new Object(), new Object()));
        assertEquals(0, comparator.compare("apples", "oranges"));
        assertEquals("Ordering.allEqual()", comparator.toString());

        List<String> strings = ImmutableList.of("b", "a", "d", "c");
        List<String> sortedCopy = comparator.sortedCopy(strings);
        assertEquals(strings, sortedCopy);
        ImmutableList<String> immutableSortedCopy = comparator.immutableSortedCopy(strings);
        assertEquals(strings, immutableSortedCopy);
    }

    /**
     * 2、natural 不能有null
     */
    public void testNatural() {
        Ordering<Integer> comparator = Ordering.natural();
        try {
            comparator.compare(1, null);
            fail();
        } catch (NullPointerException expected) {
        }
        try {
            comparator.compare(null, 2);
            fail();
        } catch (NullPointerException expected) {
        }
        try {
            comparator.compare(null, null);
            fail();
        } catch (NullPointerException expected) {
        }
        assertEquals("Ordering.natural()", comparator.toString());
    }

    /**
     * 3、List集合 复杂排序示例
     */
    public void testComplicatedOrderingExample() {
        Ordering<Iterable<Integer>> example = Ordering.<Integer>natural().nullsFirst().reverse().lexicographical().reverse().nullsLast();

        List<Integer> list1 = Lists.newArrayList();
        List<Integer> list2 = Lists.newArrayList(1);
        List<Integer> list3 = Lists.newArrayList(1, 1);
        List<Integer> list4 = Lists.newArrayList(1, 2);
        List<Integer> list5 = Lists.newArrayList(1, null, 2);
        List<Integer> list6 = Lists.newArrayList(2);

        Integer nullInt = null;
        List<Integer> list7 = Lists.newArrayList(nullInt);
        List<Integer> list8 = Lists.newArrayList(nullInt, nullInt);
        List<List<Integer>> list = Lists.newArrayList(list1, list2, list3, list4, list5, list6, list7, list8, null);

        List<List<Integer>> sorted = example.sortedCopy(list);

        /**
         * [null, null]
         * [null]
         * [1, null, 2]
         * [1, 1]
         * [1, 2]
         * [1]
         * [2]
         * []
         * null
         */
        sorted.forEach(System.out::println);
    }

    /**
     * 4、from 把给定的 Comparator 转化为排序器
     */
    public void testFrom() {
        // String.CASE_INSENSITIVE_ORDER 按照 ASCII 排序
        Ordering<String> caseInsensitiveOrdering = Ordering.from(String.CASE_INSENSITIVE_ORDER);
        assertTrue(caseInsensitiveOrdering.compare("A", "a") == 0);
        assertTrue(caseInsensitiveOrdering.compare("a", "B") < 0);
        assertTrue(caseInsensitiveOrdering.compare("B", "a") > 0);

        ArrayList<String> list = Lists.newArrayList("dehua", "abcdef", "ABCDEF", "rapido", "lbsse","lasse");
        List<String> sortedCopy = caseInsensitiveOrdering.sortedCopy(list);
        sortedCopy.forEach(System.out::println);
    }

    /*
     * 5、explicit(ExplicitOrdering)返回一个Ordering,根据它们的传入的顺序比较对象。只能比较参数列表中存在的对象
     */
    public void testExplicit_none() {
        Comparator<Integer> c = Ordering.explicit(Collections.emptyList());
        try {
            c.compare(0, 0);
        } catch (Exception e) {
//            e.printStackTrace();
        }
        assertEquals("Ordering.explicit([])", c.toString());
    }

    public void testExplicit_one() {
        Comparator<Integer> c = Ordering.explicit(0);
        assertEquals(0, c.compare(0, 0));
        try {
            c.compare(0, 1);
            fail();
        } catch (Exception e) {
//            e.printStackTrace();
        }
        assertEquals("Ordering.explicit([0])", c.toString());
    }

    public void testExplicit_two() {
//        Comparator<Integer> c = Ordering.explicit(42, 5);
//        assertEquals(0, c.compare(5, 5));
//        assertTrue(c.compare(5, 42) > 0);
//        assertTrue(c.compare(42, 5) < 0);

        Comparator<Integer> c = Ordering.explicit(5, 10);
        assertEquals(0, c.compare(5, 5));
        assertTrue(c.compare(5, 10) < 0);
        assertTrue(c.compare(10, 5) > 0);
        try {
            c.compare(5, 9);
            fail();
        } catch (Exception e) {
            System.out.println(e.getMessage());
        }
    }

    public void testExplicit_three() {
        // explicit:根据传入对象的顺序排序
        Double first = 0.2;
        Double[] second = {0.1, 0.3, 0.5};
        List<Double> numbers = Lists.asList(first, second);

        //排序比较器:根据原始的大小排序
        Ordering<Double> peopleOrdering = new Ordering<Double>() {
            @Override
            public int compare(Double left, Double right) {
                return Doubles.compare(left, right);
            }
        };
        peopleOrdering.reverse().explicit(numbers).sortedCopy(numbers).forEach(System.out::println);//[ 0.2,0.1, 0.3, 0.5]
    }


    public void testExplicit_sortingExample() {
        Comparator<Integer> c = Ordering.explicit(2, 8, 6, 1, 7, 5, 3, 4, 0, 9);
        List<Integer> list = Arrays.asList(0, 3, 5, 6, 7, 8, 9);
        Collections.sort(list, c);

        // 8, 6, 7, 5, 3, 0, 9
        list.forEach(System.out::println);
    }

    /**
     * key重复异常
     */
    public void testExplicit_withDuplicates() {
        try {
            Ordering.explicit(1, 2, 3, 4, 2);
            fail();
        } catch (IllegalArgumentException expected) {
            expected.printStackTrace();
        }
    }


    /**
     * 6、arbitrary 返回所有对象的任意顺序
     */
    public void testArbitrary_withoutCollisions() {
        List<Integer> list = Lists.newArrayList();
        for (int i = 0; i < 50; i++) {
            list.add(i);
        }

        Ordering<Object> arbitrary = Ordering.arbitrary();
        Collections.sort(list, arbitrary);

        list.forEach(System.out::println);

        assertEquals("Ordering.arbitrary()", arbitrary.toString());
    }

    /**
     * 7、usingToString
     * 按对象的字符串形式做字典排序 [lexicographical ordering]
     */
    public void testUsingToString() {
        Ordering<Object> ordering = Ordering.usingToString();
        assertEquals("Ordering.usingToString()", ordering.toString());

        List<String> list = Lists.newArrayList("lasse", "jerry", "harry", "eva", "jhon", "neron");
        System.out.println("list:" + list);

        // 使用Comparable类型的自然顺序, 例如:整数从小到大,字符串是按字典顺序;
        Ordering<String> naturalOrdering = Ordering.natural();

        // 使用toString()返回的字符串按字典顺序进行排序;
        Ordering<Object> usingToStringOrdering = Ordering.usingToString();

        // 返回一个所有对象的任意顺序
        Ordering<Object> arbitraryOrdering = Ordering.arbitrary();

        System.out.println("naturalOrdering:" + naturalOrdering.sortedCopy(list));
        System.out.println("usingToStringOrdering:" + usingToStringOrdering.sortedCopy(list));
        System.out.println("arbitraryOrdering:" + arbitraryOrdering.sortedCopy(list));
    }

    /**
     * 8、reverse 取返
     */
    public void testReverse() {
        List<String> list = Lists.newArrayList("lasse", "jerry", "harry", "eva", "jhon", "neron");
        Collections.sort(list, Ordering.natural().reverse());

        list.forEach(System.out::println);
    }

    private enum StringLengthFunction implements Function<String, Integer> {
        StringLength;

        @Override
        public Integer apply(String string) {
            return string.length();
        }
    }

    /**
     * 9、onResultOf 将传入function应用到每个元素上面,再通过Ordering进行排序。
     */
    public void testOnResultOf_1() {
        // 外部枚举函数
        Ordering<String> ordering = Ordering.natural().onResultOf(StringLengthFunction.StringLength);
        assertTrue(ordering.compare("to", "be") == 0);
        assertTrue(ordering.compare("or", "not") < 0);
        assertTrue(ordering.compare("that", "to") > 0);
        assertEquals("Ordering.natural().onResultOf(StringLength)", ordering.toString());

        ArrayList<String> list = Lists.newArrayList("lasse", "abcds", "ABCDEF", "rapido", "chengxumiao");
        ordering.sortedCopy(list).forEach(System.out::println);
    }

    public void testOnResultOf_2() {
        // 匿名内部类函数
        Ordering<String> ordering = Ordering.natural().onResultOf(new Function<String, Comparable>() {
            @Override
            public Comparable apply(@Nullable String input) {
                return input.length();
            }
        });

        ArrayList<String> list = Lists.newArrayList("lasse", "abcds", "ABCDEF", "rapido", "chengxumiao");
        ordering.sortedCopy(list).forEach(System.out::println);
    }

    public void testOnResultOf_3() {
        // lambda 表达式函数
        Ordering<String> ordering = Ordering.natural().reverse().onResultOf(str -> str.length());
        ArrayList<String> list = Lists.newArrayList("lasse", "abcds", "ABCDEF", "rapido", "chengxumiao");
        ordering.sortedCopy(list).forEach(System.out::println);
    }

    /**
     * 10、nullsFirst
     */
    public void testNullsFirst_NullsLast() {
        ArrayList<String> list = Lists.newArrayList("lasse", null, "abcds", "ABCDEF", null, "rapido", "chengxumiao");
        Collections.sort(list, Ordering.natural().nullsFirst());
        list.forEach(System.out::println);

        Ordering.natural().nullsLast().sortedCopy(list).forEach(System.out::println);

    }

    /**
     * 11、NullsLast
     */
    public void testNullsLast() {
        ArrayList<String> list = Lists.newArrayList("tingfeng", null, "abcds", "ABCDEF", null, "rapido", "chengxumiao");
        Ordering.natural().nullsLast().sortedCopy(list).forEach(System.out::println);
    }

    /**
     * 12、isOrdered 下一个元素大于或等于上一个元素,返回true
     */
    public void testIsOrdered() {
        Ordering<Comparable> ordering = Ordering.natural();

        assertFalse(ordering.isOrdered(asList(5, 3, 0, 9)));
        assertFalse(ordering.isOrdered(asList(0, 5, 3, 9)));

        assertTrue(ordering.isOrdered(asList(0, 3, 5, 9)));
        assertTrue(ordering.isOrdered(asList(0, 0, 3, 3)));
        assertTrue(ordering.isOrdered(asList(0, 3)));
        assertTrue(ordering.isOrdered(Collections.singleton(1)));
        assertTrue(ordering.isOrdered(Collections.<Integer>emptyList()));
    }

    /**
     * 13、isStrictlyOrdered 下一个元素大于上一个元素,返回true
     */
    public void testIsStrictlyOrdered() {
        Ordering<Comparable> ordering = Ordering.natural();

        assertFalse(ordering.isStrictlyOrdered(asList(5, 3, 0, 9)));
        assertFalse(ordering.isStrictlyOrdered(asList(0, 5, 3, 9)));
        assertFalse(ordering.isStrictlyOrdered(asList(0, 0, 3, 3)));

        assertTrue(ordering.isStrictlyOrdered(asList(0, 3, 5, 9)));
        assertTrue(ordering.isStrictlyOrdered(asList(0, 3)));
        assertTrue(ordering.isStrictlyOrdered(Collections.singleton(1)));
        assertTrue(ordering.isStrictlyOrdered(Collections.<Integer>emptyList()));
    }


    /**
     * 判断集合是否只读
     */
    private static void assertListImmutable(List<Integer> result) {
        try {
            result.set(0, 1);
            fail();
        } catch (UnsupportedOperationException expected) {
            // pass
        }
    }

    /**
     * 14、leastOf 有点类似截取集合前几位的概念
     */
    public void testLeastOfIterable_simple_1() {
        List<Integer> result = Ordering.natural().leastOf(Arrays.asList(3, 4, 5, -1), 2);
        assertTrue(result instanceof RandomAccess);
        assertListImmutable(result);
        assertEquals(ImmutableList.of(-1, 3), result);
    }

    public void testLeastOfIterator_simple_1() {
        List<Integer> result = Ordering.natural().leastOf(Iterators.forArray(3, 4, 5, -1), 2);
        assertTrue(result instanceof RandomAccess);
        assertListImmutable(result);
        assertEquals(ImmutableList.of(-1, 3), result);
    }

    public void testLeastOfIterable_simple_nMinusOne_withNullElement() {
        List<Integer> list = Arrays.asList(3, null, 5, -1);
        List<Integer> result = Ordering.natural().nullsLast().leastOf(list, list.size() - 1);
        assertTrue(result instanceof RandomAccess);
        assertListImmutable(result);
        assertEquals(ImmutableList.of(-1, 3, 5), result);
    }

    /**
     * 15、min 和 max
     */
    public void testIteratorMinAndMax() {
        Ordering<Comparable> ordering = Ordering.natural();
        List<Integer> ints = Lists.newArrayList(5, 3, 0, 9);
        assertEquals(9, (int) ordering.max(ints));
        assertEquals(0, (int) ordering.min(ints));

        assertEquals(9, (int) ordering.max(ints.iterator()));
        assertEquals(0, (int) ordering.min(ints.iterator()));

        assertEquals(9, (int) ordering.max(ints.listIterator()));
        assertEquals(0, (int) ordering.min(ints.listIterator()));

        // 当值相同时,返回第一个参数,此处a正确,b就不正确
        Integer a = new Integer(4);
        Integer b = new Integer(4);
        ints = Lists.newArrayList(a, b, b);
        assertSame(a, ordering.max(ints.iterator()));
        assertSame(a, ordering.min(ints.iterator()));
    }

    public void testIteratorMinExhaustsIterator() {
        List<Integer> ints = Lists.newArrayList(9, 0, 3, 5);
        Iterator<Integer> iterator = ints.iterator();
        assertEquals(0, (int) Ordering.natural().min(iterator));
        assertFalse(iterator.hasNext());
    }

    public void testIteratorMaxExhaustsIterator() {
        List<Integer> ints = Lists.newArrayList(9, 0, 3, 5);
        Iterator<Integer> iterator = ints.iterator();
        assertEquals(9, (int) Ordering.natural().max(iterator));
        assertFalse(iterator.hasNext());
    }

}

到了这里,关于Guava:Ordering 排序工具的文章就介绍完了。如果您还想了解更多内容,请在右上角搜索TOY模板网以前的文章或继续浏览下面的相关文章,希望大家以后多多支持TOY模板网!

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处: 如若内容造成侵权/违法违规/事实不符,请点击违法举报进行投诉反馈,一经查实,立即删除!

领支付宝红包 赞助服务器费用

相关文章

  • 【Java技术专题】「Guava开发指南」手把手教你如何进行使用Guava工具箱进行开发系统实战指南(基础编程篇)

    Preconditions(前置条件):让方法调用的前置条件判断更简单 。 Guava在Preconditions 类中提供了若干前置条件判断的实用方法,我们强烈建议在 Eclipse 中静态导入这些方法。每个方法都有三个变种: 当方法没有额外参数时,抛出的异常中不包含错误消息,这会使得调用方很难确

    2024年02月07日
    浏览(71)
  • Google 开源库Guava详解(集合工具类)—Maps、Multisets、Multimaps

    Maps有许多很酷的实用程序,值得单独解释。 Maps.uniqueIndex(Iterable,Function)解决了一个常见的情况,即有一堆对象,每个对象都有一些唯一的属性,并希望能够根据该属性查找这些对象。 假设我们有一堆字符串,我们知道它们有唯一的长度,我们希望能够查找具有特定长度

    2024年02月03日
    浏览(43)
  • com.google.guava:guava 组件安全漏洞及健康分析

    维护者 google组织 许可证类型 Apache-2.0 首次发布 2010 年 4 月 26 日 最新发布时间 2023 年 8 月 1 日 GitHub Star 48189 GitHub Fork 10716 依赖包 28,694 依赖存储库 219,576 Guava 是 Google 的一组核心 Java 库,其中包括新的集合类型(例如 multimap 和 multiset)、不可变集合、图形库以及用于并发、

    2024年02月10日
    浏览(47)
  • Guava RateLimiter预热模型

    本文已收录至我的个人网站:程序员波特,主要记录Java相关技术系列教程,共享电子书、Java学习路线、视频教程、简历模板和面试题等学习资源,让想要学习的你,不再迷茫。 我们都知道在做运动之前先得来几组拉伸之类的动作,给身体做个热身,让我们的身体平滑过渡到

    2024年01月18日
    浏览(33)
  • Guava RateLimiter限流

    令牌桶是按照固定速率往桶中添加令牌,请求是否被处理需要看桶中令牌是否足够,当令牌数减为零时则拒绝新的请求;漏桶则是按照常量固定速率流出请求,流入请求速率任意,当流入的请求数累积到漏桶容量时,则新流入的请求被拒绝; 令牌桶限制的是平均流入速率,允

    2024年02月10日
    浏览(37)
  • Guava Cache 介绍

    Guava 是 Google 提供的一套 Java 工具包,而 Guava Cache 是该工具包中提供的一套完善的 JVM 级别高并发缓存框架;本文主要介绍它的相关功能及基本使用,文中所使用到的软件版本:Java 1.8.0_341、Guava 32.1.3-jre。 缓存在很多情况下非常有用。例如,当某个值的计算或检索代价很高,

    2024年02月05日
    浏览(42)
  • 再见,Guava!再见,Ehcache!

    缓存(Cache)在代码世界中无处不在。从底层的CPU多级缓存,到客户端的页面缓存,处处都存在着缓存的身影。缓存从本质上来说,是一种空间换时间的手段,通过对数据进行一定的空间安排,使得下次进行数据访问时起到加速的效果。 就Java而言,其常用的缓存解决方案有很多

    2024年02月13日
    浏览(34)
  • Google 开源库Guava详解

    Guava 是一组来自Google的核心Java库,包括新的集合类型(如多映射和多集)、不可变集合、图库和并发、I/O、哈希、原语、字符串等实用程序!它广泛用于Google中的大多数Java项目,也被许多其他公司广泛使用。 Guava 开发要求 : JRE风格需要JDK 1.8或更高版本。 如果您需要支持

    2024年02月09日
    浏览(42)
  • Java中的Guava是什么?

    Java中的Guava是一个非常强大的Java库,它提供了很多实用的工具类和方法,可以帮助我们更高效地开发Java应用程序。从新手的角度来看,Guava可以让我们在Java编程中变得更加简单、快速和高效。 Guava的命名来源于“Google’s favorite Java library”(谷歌最喜欢的Java库)。它是由G

    2024年02月14日
    浏览(28)
  • Guava Cache介绍-面试用

    Guava Cache是本地缓存,数据读写都在一个进程内,相对于分布式缓存redis,不需要网络传输的过程,访问速度很快,同时也受到 JVM 内存的制约,无法在数据量较多的场景下使用。 基于以上特点,本地缓存的主要应用场景为以下几种: 对于访问速度有较大要求 存储的数据不经

    2024年02月07日
    浏览(37)

觉得文章有用就打赏一下文章作者

支付宝扫一扫打赏

博客赞助

微信扫一扫打赏

请作者喝杯咖啡吧~博客赞助

支付宝扫一扫领取红包,优惠每天领

二维码1

领取红包

二维码2

领红包