【JAVA集合框架之List与Set】
一、概述
JAVA的集合框架中定义了一系列的类,这些类都是存储数据的容器。与数组、StringBuffer(StringBuilder)相比,它的特点是:
1.用于存储对象。
2.集合长度可变。
3.不可以存储基本数据类型。
比较三种容器的特点:
数组必须存放同一种元素。
StringBuffer必须转换成字符串才能使用,如果想拿出单独的一个元素几乎不可能。
数据有很多使用对象存,对象有很多,使用集合存。
集合容器因为内部的数据结构不同有多种具体容器,不断的向上抽取就形成了集合框架。
框架的顶层就是Collection接口。
二、Collection接口
Set接口和List接口都实现了Collection接口,因此很明显的,Collection接口中存放的是Set接口和List接口的共性内容。
Collection接口中的方法:
1.添加。
boolean |
add(E e) 确保此 collection 包含指定的元素(可选操作)。 |
boolean |
addAll(Collection<? extends E> c) 将指定 collection 中的所有元素都添加到此 collection 中(可选操作)。 |
其中,参数E可暂时理解为Object(实际上在JDK1.4之前使用的一直都是Object)。
2.删除
boolean |
remove(Object o) 从此 collection 中移除指定元素的单个实例,如果存在的话(可选操作)。 |
boolean |
removeAll(Collection<?> c)
移除此 collection 中那些也包含在指定 collection 中的所有元素(可选操作)。 |
void |
clear() 移除此 collection 中的所有元素(可选操作)。 |
3.判断
boolean |
contains(Object o) 如果此 collection 包含指定的元素,则返回 true。 |
boolean |
containsAll(Collection<?> c)
如果此 collection 包含指定 collection 中的所有元素,则返回 true。 |
boolean |
isEmpty() 如果此 collection 不包含元素,则返回 true。 |
4.获取。
int |
size() 返回此 collection 中的元素数。 |
Iterator<E> |
iterator() 返回在此 collection 的元素上进行迭代的迭代器。 |
5.其它
boolean |
retainAll(Collection<?> c) 仅保留此 collection 中那些也包含在指定 collection 的元素(可选操作)。 |
Object[] |
toArray() 返回包含此 collection 中所有元素的数组。 |
|
|
toArray(T[] a)
返回包含此 collection 中所有元素的数组;返回数组的运行时类型与指定数组的运行时类型相同。 |
这是比较常用的方法,还有一些继承的方法等略。
以上方法比较常用的还是存和取的方法。
6.代码示例:
1 package p01.BaseCollectionDemo; 2 3 import java.util.ArrayList; 4 import java.util.Collection; 5 import java.util.Iterator; 6 public class CollectionDemo01 { 7 public static void main(String args[]) 8 { 9 //show1(); 10 //show2(); 11 //show3(); 12 //show4(); 13 show5(); 14 15 } 16 private static void show5() { 17 /* 18 * 演示retainAll、toArray方法 19 */ 20 Collection coll=new ArrayList(); 21 coll.add("abc1"); 22 coll.add("abc2"); 23 coll.add("abc3"); 24 coll.add("abc4"); 25 System.out.println(coll); 26 Collection coll1=new ArrayList(); 27 coll1.add("abc1"); 28 coll1.add("abc3"); 29 coll1.add("abc4"); 30 coll1.add("abc8"); 31 System.out.println(coll1); 32 33 System.out.println(coll.retainAll(coll1)); 34 System.out.println(coll);//与removeAll相反,只取相同的部分 35 36 } 37 private static void show4() { 38 39 /* 40 * 演示size、Iterator 41 */ 42 Collection coll=new ArrayList(); 43 coll.add("abc1"); 44 coll.add("abc2"); 45 coll.add("abc3"); 46 coll.add("abc4"); 47 System.out.println(coll); 48 System.out.println(coll.size()); 49 for(Iterator it=coll.iterator();it.hasNext();) 50 { 51 System.out.println(it.next()); 52 } 53 } 54 private static void show3() { 55 /* 56 * 演示contains、containsAll、isEmpty方法 57 */ 58 Collection coll=new ArrayList(); 59 coll.add("abc1"); 60 coll.add("abc2"); 61 coll.add("abc3"); 62 coll.add("abc4"); 63 System.out.println(coll); 64 Collection coll1=new ArrayList(); 65 coll1.add("abc5"); 66 coll1.add("abc6"); 67 coll1.add("abc7"); 68 coll1.add("abc8"); 69 System.out.println(coll1); 70 71 coll.addAll(coll1); 72 System.out.println(coll); 73 74 System.out.println(coll.containsAll(coll1)); 75 System.out.println(coll.contains("abc1")); 76 coll.remove("abc1"); 77 System.out.println(coll.contains("abc1")); 78 79 coll.clear(); 80 System.out.println(coll.isEmpty()); 81 82 } 83 private static void show2() { 84 /* 85 * 演示remove、removeAll、clear方法 86 */ 87 Collection coll=new ArrayList(); 88 coll.add("abc1"); 89 coll.add("abc2"); 90 coll.add("abc3"); 91 coll.add("abc4"); 92 System.out.println(coll); 93 Collection coll1=new ArrayList(); 94 coll1.add("abc5"); 95 coll1.add("abc6"); 96 coll1.add("abc7"); 97 coll1.add("abc8"); 98 System.out.println(coll1); 99 100 coll.addAll(coll1); 101 System.out.println(coll); 102 103 coll.removeAll(coll1); 104 System.out.println(coll); 105 106 coll.remove("abc1"); 107 System.out.println(coll); 108 109 coll.clear(); 110 System.out.println("打印集合元素:"+coll); 111 } 112 public static void show1() 113 { 114 /* 115 * 演示add、addAll 116 */ 117 Collection coll=new ArrayList(); 118 coll.add("abc1"); 119 coll.add("abc2"); 120 coll.add("abc3"); 121 coll.add("abc4"); 122 System.out.println(coll); 123 Collection coll1=new ArrayList(); 124 coll1.add("abc5"); 125 coll1.add("abc6"); 126 coll1.add("abc7"); 127 coll1.add("abc8"); 128 System.out.println(coll1); 129 130 coll.addAll(coll1); 131 System.out.println(coll); 132 } 133 }
三、迭代器。
1.遍历。
框架中有一个很重要的接口Iterator,使用这个接口可以遍历框架中其它所有的容器。在Collection接口中有一个方法为
boolean |
removeAll(Collection<?> c) 移除此 collection 中那些也包含在指定 collection 中的所有元素(可选操作)。 |
使用这个方法可以得到实现了Iterator接口的对象,使用这个对象的hasNext方法以及Next方法就可以得到容器中所有的对象。
boolean |
hasNext() 如果仍有元素可以迭代,则返回 true。 |
E |
next()
返回迭代的下一个元素。 |
两种遍历的方式很像,但是又有些不同,推荐使用第一种。
1 package p01.BaseCollectionDemo; 2 3 import java.util.ArrayList; 4 import java.util.Collection; 5 import java.util.Iterator; 6 7 8 public class IteratorDemo { 9 10 public static void main(String[] args) { 11 Collection coll=new ArrayList(); 12 coll.add("abc1"); 13 coll.add("abc2"); 14 coll.add("abc3"); 15 coll.add("abc4"); 16 17 Demo01(coll); 18 Demo02(coll); 19 20 21 } 22 23 private static void Demo02(Collection coll) { 24 Iterator it=coll.iterator(); 25 while(it.hasNext()) 26 { 27 System.out.print(it.next()+" "); 28 } 29 System.out.println(); 30 } 31 32 private static void Demo01(Collection coll) { 33 for(Iterator it=coll.iterator();it.hasNext();) 34 { 35 System.out.print(it.next()+" "); 36 } 37 System.out.println(); 38 } 39 40 }
分析:第一种方式遍历集合的特点就是遍历完成之后迭代器对象会随着for循环结束而在内存中被清除;而第二种方式虽然达到了遍历的效果,但是循环结束之后迭代器所占用的内存并没有被释放,浪费了一部分内存。
2.迭代原理
由于每一种容器内部的数据结构可能都不同,只是用一种接口怎么才能达到遍历个各种容器的目的呢?
分析:容器内部都维护着一个实现了Iterator接口的对象,每个对象在容器内部的操作均不同(它们仅操作本类内部的成员),但是提供了同样的遍历方法:hasNext和Next,通过这两个方法,就可以得到容器内所有的对象了。也就是说Iterator对象必须依赖于具体的容器,因为每一种容器的数据结构都不相同。对于使用容器者而言,具体的实现并不重要,只要通过容器获取到该实现的迭代器的对象即可,也就是iterator方法。Iterator接口也就是对所有Collection容器进行元素取出的公共接口。
通过查看源码即可证明:
Collection接口中声明了抽象方法iterator。
ArrayList则重写了这个方法:
我们比较在意的是Itr这个类,这个类通过返回类型可以得知是实现了Iterator接口的类:
由此,可以发现Itr类是ArrayList类的内部类。不仅ArrayList类,其它在Collection集合中的类都是这种实现方法。
四、List和Set概述。
List:列表。元素可以重复,有序(存入和取出有特定的顺序)。
Set:集合。元素不允许重复,无序(有时候有序,特别是经过特殊处理的时候比如在TreeSet中更是如此)。
注意:元素是否允许重复是List和Set的最大区别。