guava

guava 模块

Basic utilities

更方便的使用java

避免使用空值

reason:

95%的集合不应该接受null值,快速失败优于接受null值

为何使用null?

null表达的意义不明确,e.g map.get(key) 返回null,可能代表map中包含了这个值为null,或者根本不包含这个key值.

option :

创建一个option:
1. Optional.of(T) 返回一个非空的集合,如果是空会快速失败
2. Optional.absent() 直接返回一个空对象
3. Optional.fromNullable(T) 返回一个可空的集合.
查询方法:
1. boolean isPresent() 如果不为空返回true
2. T get() 返回包含的值,否则返回 IllegalStateException
3. T or(T) 返回包含的值,否则返回 default 值
4. T orNull() 返回包含的值,否则返回 null

考虑的关键点:

就算返回null, 在包装之后调用方液必须考虑返回值为空的情况.

方便的使用方法:

1. 方便的使用默认值代替null
   Objects.firstNonNull(T, T) 返回第一个不为空的值,都为空,返回nullpointer.
2. 使用 option.or 可以代替上述方法.

Preconditions 先决条件

API 使用方式:

1. 直接抛出异常
    checkArgument(i >= 0);
2. 抛出额外的Object的message ,调用 extra object.toString
    checkArgument(i >= 0,"error Message");
3. 使用未知替换符 %s
    checkArgument(i < j, "Expected i < j, but %s > %s", i, j);
方法 描述 异常
checkArgument(boolean) 检查参数是否是true IllegalArgumentException
checkNotNull(T) 检查参数是否是null NullPointerException
checkState(boolean) 检查当前对象的状态,与入参无关的状态 IllegalStateException
checkElementIndex(int index, int size) 检查当前未知是否在元素中 IndexOutOfBoundsException

Cache

example :

   LoadingCache graphs = CacheBuilder.newBuilder()
   .maximumSize(1000)
   .expireAfterWrite(10, TimeUnit.MINUTES)
   .removalListener(MY_LISTENER)
   .build(
       new CacheLoader() {
         public Graph load(Key key) throws AnyException {
           return createExpensiveGraph(key);
         }
   });

使用范围:

cache 和 ConcurrentMap 很相似,但是也有区别.
ConcurrentMap 保存所有已插入的项目直到呗明确的移除.
cache 自动删除内存中过期的数据.
LoadingCache 可以在内存中没有时,自动加载数据

* 使用更多的内存,加快速递
* 需要查询多次相同的key值
* 不会使用过多的内存.

使用方式:

是否可以使用去计算一个key值.
Y : 使用CacheLoader
N : 传入Callable进入get方法
  1. 使用cacheLoader方式
这里内部加载缓存的方法会抛出检查性异常,会在get方法获取时抛出ExecutionException.
LoadingCache graphs = CacheBuilder.newBuilder()
       .maximumSize(1000)
       .build(
           new CacheLoader() {
             public Graph load(Key key) throws AnyException {
               return createExpensiveGraph(key);
             }
           });

...
try {
  return graphs.get(key);
} catch (ExecutionException e) {
  throw new OtherException(e.getCause());
}

非检查性异常方式:

LoadingCache graphs = CacheBuilder.newBuilder()
       .expireAfterAccess(10, TimeUnit.MINUTES)
       .build(
           new CacheLoader() {
             public Graph load(Key key) { // no checked exception
               return createExpensiveGraph(key);
             }
           });

...
return graphs.getUnchecked(key);
  1. 使用Callable:

    Cache cache = CacheBuilder.newBuilder()
        .maximumSize(1000)
        .build(); // look Ma, no CacheLoader
    ...
    try {
      // If the key wasn't in the "easy to compute" group, we need to
      // do things the hard way.
      cache.get(key, new Callable() {
        @Override
        public Value call() throws AnyException {
          return doThingsTheHardWay(key);
        }
      });
    } catch (ExecutionException e) {
      throw new OtherException(e.getCause());
    }
    

过期策略:

  1. Size-based Eviction 基于大小的过期策略 :
    CacheBuilder.maximumSize(long) 大小不超过参数值.
    CacheBuilder.maximumWeight(long) 计算传入参数的大小(内存大小值等)
        LoadingCache graphs = CacheBuilder.newBuilder()
           .maximumWeight(100000)
           .weigher(new Weigher() {
              public int weigh(Key k, Graph g) {
                return g.vertices().size();
              }
            })
           .build(
               new CacheLoader() {
                 public Graph load(Key key) { // no checked exception
                   return createExpensiveGraph(key);
                 }
           }
        );
    
  2. 基于时间的过期策略:
    expireAfterAccess(long, TimeUnit) 基础时间内没有访问过
    expireAfterWrite(long, TimeUnit) 基础时间内有过创建或有过更改

你可能感兴趣的:(guava)