Google Guava 快速入门 —— 新集合介绍

Google Guava 快速入门.jpg

Guava 集合工具

Guava引进了JDK里没有的,但是非常有用的一些新的集合类型。所有这些新集合类型都能和JDK里的集合平滑集成。本篇文章只是简单介绍到了很少一部分,还有很多子类需要逐步使用过程中去探索。

一、Guava 新集合

集合名称说明
Multiset把重复的元素放入一个集合。
Multimap一个 key 对应多个 value。
BiMapkey 和 value 都不能重复。
Table表代表一个特殊的图,其中两个键可以在组合的方式被指定为单个值。
--

1、Multiset 重复的元素放入一个集合

可以用两种方式看待 Multiset

  • 没有元素顺序限制的 ArrayList<E>

  • Map<E, Integer>,键为元素,值为计数

2、Multimaps 一个 key 对应多个 value

每个有经验的Java程序员都在某处实现过 Map<K, List<V>> 或 Map<K, Set<V>>,并且要忍受这个结构的笨拙。

例如,Map<K, Set<V>> 通常用来表示非标定有向图。Guava的 Multimap 可以很容易地把一个键映射到多个值。换句话说,Multimap是把键映射到任意多个值的一般方式。

3、BiMap key 和 value 都不能重复

BiMap<K, V> 是特殊的Map:

  • 可以用 inverse() 反转 BiMap<K, V> 的键值映射

  • 保证值是唯一的,因此 values() 返回Set而不是普通的Collection

二、Immutable 不可变集合

不可变集合,顾名思义就是说集合是不可被修改的。集合的数据项在创建的时候提供,并且在整个生命周期中都不可改变。

1、为什么使用不可变集合?

  • 线程安全的:immutable对象在多线程下安全

  • 不需要支持可变性, 可以尽量节省空间和时间的开销. 所有的不可变集合实现都比可变集合更加有效的利用内存

  • 可以被使用为一个常量,并且期望在未来也是保持不变的

2、怎么使用不可变集合

不可变集合可以用如下多种方式创建:

  • copyOf方法:如 ImmutableSet.copyOf(set);

  • of方法:如 ImmutableSet.of(“a”, “b”, “c”) 或 ImmutableMap.of(“a”, 1, “b”, 2);

  • Builder工具:如

    public static final ImmutableSet<Color> GOOGLE_COLORS =
          ImmutableSet.<Color>builder()
              .addAll(WEBSAFE_COLORS)
              .add(new Color(0, 191, 255))
              .build();

此外,对有序不可变集合来说,排序是在构造集合的时候完成的,例如:ImmutableSortedSet.of("a", "b", "c", "a", "d", "b")

3、JDK 的不可变集合

JDK也提供了 Collections.unmodifiableXXX 方法把集合包装为不可变形式,但是存在一些问题,最少存在以下几点不足:

  • 笨拙:因为你每次都得写那么多代码;

  • 不安全:如果没有引用到原来的集合,这种情况之下才会返回唯一真正永恒不变的集合;

  • 效率很低:返回的不可修改的集合数据结构仍然具有可变集合的所有开销。

将一个对象复制一份成 immutable 的,是一个防御性编程技术。在JDK类库中很多集合(List、Set、Map等) 都可以调用 Collections 类提供的静态方法 unmodifiableXXX(…) 来得到一个不可修改的视图,如下所示:

List list = new ArrayList();
list.add("wyp");list.add("good");
List unmodifiableList = Collections.unmodifiableList(list);
System.out.println(unmodifiableList);//[wyp, good]
unmodifiableList.add("add");

上述代码利用 Collections.unmodifiableList(list) 得到一个不可修改的集合 unmodifiableList,当 unmodifiableList.add("add")时,运行代码将会出现以下异常:

Exception in thread "main" java.lang.UnsupportedOperationException
    at java.util.Collections$UnmodifiableCollection.add(Collections.java:1018)
    at com.wyp.test.testFiles(test.java:152)
    at com.wyp.test.main(test.java:160)

一切看起来很不错,因为调用 unmodifiableList.add() 会抛出一个 java.lang.UnsupportedOperationException。但,如果有用户修改了list,会发生什么情况?在上述代码的下面加入以下代码:

list.add("add");
System.out.println(unmodifiableList);

当你再次打印 unmodifiableList 的时候,你会发现结果是[wyp, good, add],多了一个add元素。unmodifiableList不是不可变的吗?这显然不是我们期望的。

说明: Collections.unmodifiableList(…)实现的不是真正的不可变集合,当原始集合被修改后,不可变集合里面的元素也是跟着发生变化。

4、关联可变集合和不可变集合

可变集合接口属于JDK还是Guava不可变版本
CollectionJDKImmutableCollection
ListJDKImmutableList
SetJDKImmutableSet
SortedSet/NavigableSetJDKImmutableSortedSet
MapJDKImmutableMap
SortedMapJDKImmutableSortedMap
MultisetGuavaImmutableMultiset
SortedMultisetGuavaImmutableSortedMultiset
MultimapGuavaImmutableMultimap
ListMultimapGuavaImmutableListMultimap
SetMultimapGuavaImmutableSetMultimap
BiMapGuavaImmutableBiMap
ClassToInstanceMapGuavaImmutableClassToInstanceMap
TableGuavaImmutableTable

三、相关文章



未经允许请勿转载:程序喵 » Google Guava 快速入门 —— 新集合介绍

点  赞 (0) 打  赏
分享到: