Guava-Java核心工具库(三)

guava

最近在公司的项目中注意到了一个依赖guava,在项目中很多地方都用到了它,特别是集合转换时大量使用,而Guava的通用性和实用性相信每一个javaer都有所体会,今天就来介绍一下这款来自Google的Java核心工具库。

官方是这样介绍Guava

Guava is a set of core Java libraries from Google that includes new collection types (such as multimap and multiset), immutable collections, a graph library, and utilities for concurrency, I/O, hashing, primitives, strings, and more! It is widely used on most Java projects within Google, and widely used by many other companies as well.

翻译过来就是,Guava 是 Google 的一组核心 Java 库,其中包括新的集合类型(例如 multimap 和 multiset)、不可变集合、图形库以及用于并发、I/O、哈希、原语、字符串等的实用程序!它被广泛用于 Google 内部的大多数 Java 项目,也被许多其他公司广泛使用。

字符串

Joiner

使用分隔符将字符串序列连接在一起可能会非常棘手,但事实并非如此。如果您的序列包含空值,则可能会更加困难。 Joiner 流畅的风格让它变得简单。

    public void test() {
        // Hello,null,World
        log.info("{}", String.join(",", "Hello", null, "World"));
    }
Joiner joiner = Joiner.on(", ").skipNulls();
// Harry, Ron, Hermione
log.info("{}", joiner.join("Harry", null, "Ron", "Hermione"));

您还可以在对象上使用 Joiner,这些对象将使用其 toString() 进行转换,然后连接。

Joiner.on(",").join(Arrays.asList(1, 5, 7)); // returns "1,5,7"

Splitter

用于分割字符串的内置 Java 实用程序有一些奇怪的行为。例如,String.split 会默默地丢弃尾随分隔符。

",a,,b,".split(",")会返回什么?正确答案是"", "a", "", "b"。丢失了最后一个空字符串,至于为什么我也不知道。Splitter 允许使用令人放心的简单流畅模式完全控制所有这些令人困惑的行为。

Splitter.on(',')
    .trimResults()
    .omitEmptyStrings()
    .split("foo,bar,,   qux");

返回一个Iterable<String>包含"foo", "bar", "qux"。Splitter 可以设置为根据任何 Pattern、char、String 或 CharMatcher 进行拆分。

MethodDescriptionExample
Splitter.on(char)根据出现的特定单个字符进行拆分。Splitter.on(';')
Splitter.on(CharMatcher)在某个类别中出现任何字符时进行拆分。Splitter.on(CharMatcher.BREAKING_WHITESPACE) Splitter.on(CharMatcher.anyOf(";,."))
Splitter.on(String)拆分文字字符串。Splitter.on(", ")
Splitter.on(Pattern) Splitter.onPattern(String)根据正则表达式进行拆分。Splitter.onPattern("\r?\n")
Splitter.fixedLength(int)将字符串拆分为指定固定长度的子字符串。最后一块可以小于 length,但绝不会为空。Splitter.fixedLength(3)

修饰

MethodDescriptionExample
omitEmptyStrings()自动从结果中省略空字符串。Splitter.on(',').omitEmptyStrings().split("a,,c,d") returns "a", "c", "d"
trimResults()修剪结果中的空格;相当于trimResults(CharMatcher.WHITESPACE)。Splitter.on(',').trimResults().split("a, b, c, d") returns "a", "b", "c", "d"
trimResults(CharMatcher)从结果中修剪与指定 CharMatcher 匹配的字符。Splitter.on(',').trimResults(CharMatcher.is('_')).split("_a ,_b_ ,c__") returns "a ", "b_ ", "c".
limit(int)返回指定数量的字符串后停止拆分。Splitter.on(',').limit(3).split("a,b,c,d") returns "a", "b", "c,d"

还可以通过使用 splitToList() 返回一个列表

Ranges

Guava 强大的 API,可用于处理可比较类型的范围,包括连续的和离散的。

List<Double> scores;
Iterable<Double> belowMedianScores = Iterables.filter(scores, Range.lessThan(median));
...
Range<Integer> validGrades = Range.closed(1, 12);
for(int grade : ContiguousSet.create(validGrades, DiscreteDomain.integers())) {
  ...
}

表达式:

  • (a..b) = {x | a < x < b}
  • [a..b] = {x | a <= x <= b}
  • [a..b) = {x | a <= x < b}
  • (a..b] = {x | a < x <= b}
  • (a..+∞) = {x | x > a}
  • [a..+∞) = {x | x >= a}
  • (-∞..b) = {x | x < b}
  • (-∞..b] = {x | x <= b}
  • (-∞..+∞) = 全集

对应的静态方法:

Range typeMethod
(a..b)open(C, C)
[a..b]closed(C, C)
[a..b)closedOpen(C, C)
(a..b]openClosed(C, C)
(a..+∞)greaterThan(C)
[a..+∞)atLeast(C)
(-∞..b)lessThan(C)
(-∞..b]atMost(C)
(-∞..+∞)all()
Range.closed("left", "right"); // “left”和“right”之间的所有字符串
Range.lessThan(4.0); // 严格小于4的double

Range<String> range = Range.closed("left", "right");
// false
log.info("{}", range.test("lefs"));
// true
log.info("{}", range.test("lefu"));

操作:

  1. 查询操作

    Range.closedOpen(4, 4).isEmpty(); // returns true
    Range.openClosed(4, 4).isEmpty(); // returns true
    Range.closed(4, 4).isEmpty(); // returns false
    Range.open(4, 4).isEmpty(); // Range.open throws IllegalArgumentException
    
    Range.closed(3, 10).lowerEndpoint(); // returns 3
    Range.open(3, 10).lowerEndpoint(); // returns 3
    Range.closed(3, 10).lowerBoundType(); // returns CLOSED
    Range.open(3, 10).upperBoundType(); // returns OPEN
    
  2. 区间运算

    • encloses
      • [3..6] encloses [4..5]
      • (3..6) encloses (3..6)
      • [3..6] encloses [4..4) (即使后者是空的)
      • (3..6] does not enclose [3..6]
      • [4..5] does not enclose (3..6) 即使它包含后一个范围包含的每个值,尽管使用离散域可以解决这个问题
      • [3..6] does not enclose (1..1] 即使它包含后一个范围包含的每个值
    • isConnected
      Range.closed(3, 5).isConnected(Range.open(5, 10)); // returns true
      Range.closed(0, 9).isConnected(Range.closed(3, 4)); // returns true
      Range.closed(0, 5).isConnected(Range.closed(3, 9)); // returns true
      Range.open(3, 5).isConnected(Range.open(5, 10)); // returns false
      Range.closed(1, 5).isConnected(Range.closed(6, 10)); // returns false
      
    • intersection
      Range.closed(3, 5).intersection(Range.open(5, 10)); // returns (5, 5]
      Range.closed(0, 9).intersection(Range.closed(3, 4)); // returns [3, 4]
      Range.closed(0, 5).intersection(Range.closed(3, 9)); // returns [3, 5]
      Range.open(3, 5).intersection(Range.open(5, 10)); // throws IAE
      Range.closed(1, 5).intersection(Range.closed(6, 10)); // throws IAE
      
    • span
      Range.closed(3, 5).span(Range.open(5, 10)); // returns [3, 10)
      Range.closed(0, 9).span(Range.closed(3, 4)); // returns [0, 9]
      Range.closed(0, 5).span(Range.closed(3, 9)); // returns [0, 9]
      Range.open(3, 5).span(Range.open(5, 10)); // returns (3, 10)
      Range.closed(1, 5).span(Range.closed(6, 10)); // returns [1, 10]
      

Math

JDK 未提供经过优化、经过彻底测试的数学实用程序。

根据所涉及的主要数值类型,基本独立数学函数分为 IntMath、LongMath、DoubleMath 和 BigIntegerMath 类。这些类具有并行结构,但每个类仅支持相关的功能子集。

int logFloor = LongMath.log2(n, FLOOR);

int mustNotOverflow = IntMath.checkedMultiply(x, y);

long quotient = LongMath.divide(knownMultipleOfThree, 3, RoundingMode.UNNECESSARY); // fail fast on non-multiple of 3

BigInteger nearestInteger = DoubleMath.roundToBigInteger(d, RoundingMode.HALF_EVEN);

BigInteger sideLength = BigIntegerMath.sqrt(area, CEILING);
  • 8
    点赞
  • 8
    收藏
    觉得还不错? 一键收藏
  • 打赏
    打赏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

雨路行人

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值