——- android培训、java培训、期待与您交流! ———-
1. 集合框架总论
结构框架关系图
1.1 什么是集合框架 概念(concept)
集合是某一类对象的通称,这类对象代表以某种方式组合到一起的组对象; 它是将多个元素组合为一个单元的对象,用于存储,检索,操纵和传递数据。
对象的集合,指的是对象引用的集合而不是对象的集合,在Java集合中只存储引用,对象在集合之外。
集合框架提供用于管理对象集合的接口和类,它包括接口,实现和算法。
Java集合框架提供了有效地数据结构及算法,因此程序员不需要自己编写代码实现这些功能;提供了高性能的数据结构及算法的实现。因此对各个接口的实现是可以互换的,因此程序很容易转换接口。
1.2 Collection接口
Collection代表着一组对象,这些对象成为Collection的元素。Collection接口是集合继承树中顶层的接口,该接口声明了集合中常用到的一些通用方法。这些方法都是集合框架中最基本的方法,由于其他接口都是继承collection接口,所以这些接口都继承了这些方法
2. 列表(List)
2.1 List列表接口
List接口继承自Collection接口,其中的元素可以按索引的顺序访问,所以也可以称之为有索引的Collection。实现该接口的类均属于Ordered类型,具有列表的功能,其元素顺序均是按添加(索引)的先后进行排序的。
Tips
列表接口中的方法很注重索引,如果开发人员需要对其中的每一个元素位置进行控制,并需要根据元素的索引来访问元素,可以使用实现了该接口的类来处理。
2.2 Vector类
Vector 类也成为向量,其性能特点与ArrayList基本相同。不同之处是该类的功能方法是同步的,同一时刻只能有一个线程访问,如果没有特殊需要,现在一般都使用ArrayList。
import java.util.*;
public class VectorEx
{
public static void main(String[] args)
{
//创建一个Vector对象,容量初始化为5
//这时参数与返回值都必须为String类型
Vector<String> v1 = new Vector<String>(5);
//添加一个字符串对象
v1.addElement(new String("one"));
v1.addElement("three");
v1.addElement("four");
//在位置0插入一个字符串对象
v1.insertElementAt("zero", 0);
v1.insertElementAt("two", 2);
v1.insertElementAt("five", 5);
//输出Vector对象的元素值
System.out.println("v1: "+ v1);
//输出Vector对象的容量
System.out.println("v1的容量为 "+ v1.capacity());
Vector<String> v2 = new Vector<String>(5, 1);
v2.addElement("one");
v2.addElement("three");
v2.addElement("four");
v2.insertElementAt("zero", 0);
v2.insertElementAt("two", 2);
v2.insertElementAt("five", 5);
System.out.println("v2: "+ v2);
System.out.println("v2的容量为: "+v2.capacity());
}
}
输出结果:
v1:[zero, one, two, three, four, five]
v1的容量为10
v2: [zero, one, two, three, four, five]
v2的容量为6
import java.util.*;
public class Vector2
{
public static void main(String[] args)
{
//创建Vector类的对象
Vector v = new Vector();
//初始化Vector对象中的元素
for(int i = 0; i<5 ; i++)
{
v.add(String.valueOf(i));
}
//对Vector进行操作
for(int i = 5; i<10; i++)
{
v.add(String.valueOf(9-i+5));
}
//打印Vector列表
System.out.println("这里是Vector操作后的结果: ");
System.out.println(v);
}
}
运行结果:
这里是Vector操作后的结果:
[0, 1, 2, 3, 4, 9, 8, 7, 6, 5]
2.3 ArrayList类
ArrayList是list接口最常用的实现之一,ArrayList是由数组实现的List,它提供常量事件的位置访问,而且速度很快,不需要为List中的每一个元素分配节点对象。
Tips
该类内部实际上市依赖数组实现的,因此对元素进行随机访问的性能很好。但如果进行大量插入,删除操作,此类的性能很差,并不适合。
三个构造方法
public ArrayList()
创建一个空ArrayList, 初始容量为10
public ArrayList(int initialCapacity)
创建一个Arraylist,初始容量为initialCapactiy
public ArrayList(Collection c)
创建一个ArrayList,以collection c中的元素为厨师内容的ArrayList对象。
一个使用ArrayList类的程序
import java.util.*;
public class ArrayList1
{
public static void main(String[] args)
{
//创建列表ArrayList的对象
ArrayList al = new ArrayList();
//初始化ArrayList对象中的元素
for(int i=0; i<5; i++)
{
al.add(String.valueOf(i));
}
//对ArrayList进行操作
for(int i=6; i<8; i++)
{
al.set(i-5, String.valueOf(i));
}
System.out.println("这里是ArryaList操作后的结果: ");
System.out.println(al);
//取出指定索引的元素并处理
Object o = al.get(3);
String s = (String)o;
System.out.println("索引值为3的元素长度为: "+s.length());
}
}
一个在ArrayList类中进行删除操作的程序
import java.util.*;
public class ArrayList2
{
public static void main(String[] args)
{
//创建一个ArrayList的对象
//参数与返回值都必须为String类型
ArrayList<String> col = new ArrayList<String>();
//循环加入5个字符串对象
for(int i = 0; i<5; i++)
{
col.add(String.valueOf(i));
}
System.out.println("开始时col中的元素有: ");
//遍历输出对象col中的元素
for(Iterator<String> iter = col.iterator(); iter.hasNext();)
{
System.out.println("the element is :" + iter.next());
}
//删除对象col中位置1的元素
col.remove(1);
System.out.println("在删除其中一个元素后col中的元素有: ");
//顺序输出对象col中的元素
for(int i = 0; i<col.size(); i++)
{
System.out.println("element at " + i + " is " + col.get(i));
}
}
}
2.4 LinkedList类
LinkedList类,其功能与ArrayList,Vector相同,都是列表List的实现。
其内部是依赖双链表来实现的,因此具有很好的插入,删除性能,但随即访问元素的性能相对较差,适合用在插入,删除多,元素随即访问少的场合。
LinkedLIst的构造器
public LinkedList()
//该方法将构造一个空的列表
public LinkedList(Collection c)
//构造一个包含集合collection c的所有元素的列表
一个使用LinkedList类的程序
import java.util.*;
public class LinkedList1
{
public static void main(String[] args)
{
//创建一个LinkedList类的对象
LinkedList ll = new LinkedList();
//初始化LinkedList对象
for(int i = 0; i<5; i++)
{
ll.add(String.valueOf(i));
}
//对LinkedList进行插入操作
for(int i = 5; i<10; i++)
{
ll.add(i,String.valueOf(10-i+5));
}
System.out.println("这里是LinkedList操作后的结果: ");
System.out.println(ll);
}
}
输出结果:
这里是LinkedList操作后的结果:
[0, 1, 2, 3, 4, 10, 9, 8, 7, 6]
import java.util.*;
public class LinkedList2
{
public static void main(String[] args)
{
//创建一个LinkedList的对象
//参数与返回值都必须为String类型
LinkedList<String> liList = new LinkedList<String>();
//循环加入5个字符串对象
for(int i = 0; i<5; i++)
{
liList.add(String.valueOf(i));
}
System.out.println(liList);
System.out.println(liList.get(3));
//设置位置为3的元素为 aaa
liList.set(3. "aaa");
System.out.println(liList);
//找出列表中的头元素
System.out.println(liList.peek());
System.out.println(liList);
//找出列表中的头元素并删除
System.out.println(liList.poll());
System.out.println(liList);
//获取第一个元素
System.out.println("第一个元素是"+liList.getFirst());
//获取最后一个元素
System.out.println("最后一个元素是"+liList.getLast());
}
}
输出结果:
3
[0, 1, 2, aaa, 4]
0
[0, 1, 2, aaa, 4]
0
[1, 2, aaa, 4]
第一个元素是1
最后一个元素是4
3. 集合(Set)
Set集合是一种不包含重复元素的Collection,即任意的两个元素e1和e2比较,结果都不相等。
Tips:
Set的构造函数有一个约束条件,传入的Collection参数不能包含重复的元素。必须小心操作可变对象(Mutable Object)。如果一个Set中的可变元素改变了自身状态,Object.equals(Object)=true会发生一些问题。
3.1 Set接口
Definition:
Set接口与List接口的不同之处在于List按照顺序将对象的引用添加进去,对象的引用所指向的对象没有特别的要求,而Set要求在其中的任意两个引用指向的对象equals都返回false。List中的元素有顺序,Set中的元素没有顺序。
Set接口声明如下
public interface Set<E>extends Collection<E>
3.2 SortedSet接口
SortedSet继承自Set接口,所以该接口不但具有Set的所有功能,而且是一个Sorted类型的Set。也就是说,实现该接口的类将按元素的天然顺序自动排序,不管插入的顺序是什么,其总会按照元素的天然顺序进行遍历。
SortedSet常用方法
Object first() //返回第一个元素,也是最小的元素
Object last() //返回最后一个元素,也是最大的元素
SortedSet headSet(Object toElement)
//返回一个包含所有小于toElement并且不包含toElement的SortedSet
SortedSet tailSet(Object fromElement)
//返回一个包含所有大于fromElement并且包含fromElement的SortedSet
SortedSet subSet(Object fromElement, Object toElement)
//返回从fromElement到toElement并且不包含toElement的SortedSet
3.3 TreeSet接口
TreeSet类是实现了接口SortedSet的类,是SortedSet的唯一实现形式,当需要按值排序迭代的时候,就需要使用TreeSet。此类保证排序后的set按照升序排列元素,根据使用的构造方法不同,可能会按照元素的自然顺序进行排序。
TreeSet的4种构造器
TreeSet()
TreeSet(Collection c)
TreeSet(Comparator c)
TreeSet(SortedSet s)
import java.util.*;
public class TreeSet1
{
public static void main(String[] args)
{
//创建了TreeSet的对象
TreeSet ts = new TreeSet();
//向TreeSet对象中依此添加了数组为5,6,3,2,4的字符串
ts.add(String.valueOf(5));
ts.add(String.valueOf(6));
ts.add(String.valueOf(3));
ts.add(String.valueOf(2));
ts.add(String.valueOf(4));
ts.remove(String.valueOf(5));
ts.add(String.valueOf(1));
System.out.print("TreeSet操作后的结果为: ");
System.out.println(ts);
}
}
输出结果:
TreeSet操作后的结果为:
[1, 2, 3, 4, 6]
代码分析:
从运行结果来看,元素的显示结果是按照自然的顺序呢来显示的,这个是和添加的顺序无关的。
下面是一个TreeSet类中方法的程序
import java.util.*;
public class TreeSet2
{
public static void main(String[] args)throws Exception
{
//创建一个TreeSet对象
TreeSet ts = new TreeSet();
for(int i=5; i>=0; i--)
{
ts.add(new Interger(i);
}
//复制TreeSet对象
TreeSet anotherts = (TreeSet) ts.clone();
//循环输出it对象中的元素
Iterator it = anotherts.iterator();
while(it.hasNext())
{
System.out.println(it.next());
}
System.out.println("创建TreeSet类");
//创建一个TreeSet对象
TreeSet s = new TreeSet(new Mycomparator());
s.add("aa");
s.add("cc");
s.add("bb");
s.add("dd");
//为对象s创建一个迭代器对象
Iterator its = s.iterator();
//遍历输出s中的对象
while(its.hasNext())
{
System.out.println(its.next());
}
System.out.println("第一个元素:" + ts.first());
System.out.println("最后一个元素: " + ts.last());
}
}
输出结果:
5
创建TreeSet类
aa
bb
cc
dd
第一个元素: aa
最后一个元素: dd
代码解析:
本程序首先创建了一个TreeSet对象,然后使用clone复制了一个TreeSet对象
接下来循环现实元素。 值得注意的是在最后用first方法和last方法来提取第一个元素和最后一个元素。
3.4 HashSet接口
HashSet类是Set接口最常用的实现之一,其既不是Ordered也不是Sorted,元素在其中存储不保证任何顺序。 HashSet存储对象引用时是按照哈希策略来实现的。
HashSet比TreeSet要快,但是它不提供排序保障
HashSet类的几个构造器
public HashSet()
//空的HashSet 初始容量为16
public HashSet(int inititalCapacity)
//initialCapacity的位HashSet的指定初始容量
public HashSet(Collection c)
//以C中的元素为初始内容的HashSet
import java.util.*;
public class HashSet
{
public static void main(String[] args)
{
HashSet hs = new HashSet();
hs.add(String.valueOf(5));
hs.add(String.valueOf(1));
hs.add(String.valueOf(3));
hs.add(String.valueOf(2));
hs.add(String.valueOf(4));
//删除hashSet中的5
hs.remove(String.valueOf(5));
//添加一个内容为1的字符串
hs.add(String.valueOf(1));
//将null值添加进HashSet中
hs.add(null);
System.out.println("HashSet中元素包括: ");
System.out.println(hs);
}
}
输出结果:
HashSet中元素包括:
[null, 3, 2, 1, 4]
代码分析:
**HashSet中并不保证元素的存储顺序,既不是天假顺序,也不是元素自身的顺
序。相同的元素在HashSet只出现一个,同时HashSet允许添加Null元素。**
4. 映射(Map)
概念
Map(映射)是一个存储关键字和值的关联,或者说是关键字/值对的集合,给定一个关键字可以得到其相应的值。关键字必须是唯一的,但值是可以被复制的。 而一个值对象可以使另一个Map,以此类推,就可以形成一个多级映射。在Map中,键对象是不允许重复的,为了保持查找结果的一致性。
4.1 Map接口
概念
Map也可以称之为键/值集合,因为在实现了该接口的集合中,元素都是成对出现的,一个称之为键,另一个称呼为值。 键和值都是对象,键对象用来在Map中唯一的标识一个值对象。键对象在Map中不能重复出现,就像Set中的元素不能重复一样。
Map是一个键值映射的对象,而且键不允许相同,不能包含有重复的键,每个键最多映射到一个值,所以Map看起来比较像是有映射组成的Set.
4.2 HashMap类
HashMap类是基于哈希表的Map接口的实现。该类提供所有可选的映射操作,并允许使用null值和null键。但是此类不保证映射的顺序。如果只需要获得最大的速度而不关心迭代顺序,可以使用HashMap类。
HashMap的实例有两个参数影响其性能,分别是初始容量和加载因子。容量是哈希表中桶的数量,初始容量只是哈希表在创建时的容量。加载因子是哈希表在其容量自动增加之前可以达到多满的一种尺度。当哈希表中的条目数超过了加载因子与当前容量的乘积时,通过调用rehash方法将容量翻倍。HashMap类声明如下
public class HashMap<K,V>extends AbstractMap<K,V>implements Map<K,V>, Cloneable, Serializable
HashMap类的构造器
public HashMap()
public HashMap(Map m)
import java.util.*;
public class HashMap
{
public static void main(String[] args)
{
//创建了HashMap对象
HashMap hm = new HashMap();
hm.put(1,"A");
hm.put(3,"B");
hm.put(4,"C");
hm.put(2,"D");
hm.put(5,"E");
System.out.println("添加元素后的结果为: ");
System.out.println(hm);
//移除简直为3的
hm.remove(3)
//更替简直为4的
hm.put(4,"F");
System.out.println("删除和更替以后的hm结果:");
System.out.println("hm");
//取出指定键对应的值
//返回此映射指定键值 Object get(Obejct key)
Object o = hm.get(2)
String s = (String) o;
System.out.println("键2对应的值为:" + s);
}
}
输出结果:
添加元素后的结果为:
{1=A, 2=D, 3=B, 4=C, 5=E}
删除和更替以后的hm结果:
{1=A, 2=D, 4=F, 5=E}
键2对应的值为:D
import java.util.*;
import java.util.Map.Entry;
public class HashTree2
{
public static void main(String[] args)
{
//创建一个HashMap类对象,参数与返回值都必须为String类型
HashMap<String, String> mapHash = new HashMap<String, String>();
//使用put方法添加键值对
mapHash.put("one", "A");
mapHash.put("two", "B");
mapHash.put("three", "C");
mapHash.put("four", "D");
mapHash.put("five", "E");
mapHash.put("six", "F");
mapHash.put("seven", "G");
String query = "six";
System.out.println("键值为:" + query);
//使用get方法通过键获得值
String resultString = (String)mapHash.get(query);
System.out.println("对应的值为:" + resultString);
//通过entrySet方法获取Set视图
Set<Entry<String, String>> hsm = mapHash.entrySet();
Iterator <Entry<String, String>> i = hsm.iterator();
for(i.hasNext())
{
Entry en = i.next();
System.out.println("键为: "+en。getKey()+“对应的值为:” + en.getValue());
}
}
}
输出结果
键值为six
对应的值为: F
键为:two对应的值为:B
键为:seven对应的值为:G
键为:five对应的值为:E
键为:one对应的值为:A
键为:three对应的值为:C
键为:four对应的值为:D
键为:six对应的值为:F
代码解析:
本程序中使用的是Hash码是字符串的形式,在最后使用hasNext方法来循环现实所有的元素,并同时将键和对应的值都显示出来。
4.3 TreeMap类
TreeMap类继承于AbstractMap类,同时实现了SortedMap接口,是SortedMap接口的基于红黑树的实现。该类和TreeSet相似,而且处理TreeMap的KeySet方法所得到的集合与TreeSet相同。此类保证了映射按照升序顺序排列关键字,根据使用的构造方法不同,可能会按照键的类的自然顺序进行排序(参见comparable),或者按照创建时所提供的比较器进行排序。
TreeMap类的声明如下所示
public class TreeMap<K,V>extends AbstractMap<K,V>implements SortedMap<K,V>,Cloneable, Serializable
TreeMap类提供4个构造器
public TreeMap()
//参数s为包含指定键值对的SortedMap。该构造器将构造一个以s中的键值对为初始内容的TreeMap对象
public TreeMap(SortedMap s)
//参数c为包含指定键值对的Map, 该构造器将构造一个以c中的元素为初始内容的TreeMap对象
public TreeMap(Map c)
//Comparator为指定的比较器,与TreeSet相同,如果想指定键的排序规则,则可以使用此构造器
TreeMap(Comparator comparator)
public TreeMap(SortedMap<K, ?extends V>m)
方法构造一个新的映射,包含的隐射关系与给定的SortedMap相同,该映射按照相同的排序方式进行排序,此方法以线性的时间运行。
import java.util.*
public class TreeMap
{
public static void main(String[] args)
{
TreeMap<String, String> tm = new TreeMap<String, String>()
tm.put("1", "A");
tm.put("2", "B");
tm.put("3", "C");
tm.put("4", "D");
tm.put("5", "E");
tm.put("6", "F");
//输出tm对象中的所有元素
System.out.println("所有的元素的值为: " + tm);
//为tm对象中的键值添加一个迭代器
Iterator iter = tm.keySet().iterator();
for(; iter.hasNext();)
{
System.out.println("元素值为: " + tm.get(iter.next()));
}
}
}
参考资料