JAVA学习之集合总结

来源:互联网 发布:淘宝招聘官网首页 编辑:程序博客网 时间:2024/05/01 07:01
一、集合框架的基本结构


最上层的三个接口分别是:
Collection:用于存储一个对象的,Collection 层次结构 中的根接口。
    Collection 表示一组对象,这些对象也称为 collection 的元素。
Map:用于存储两个对象
Iterator:用于集合的迭代(遍历)


Collection接口的子接口:
List接口:有序的 collection(也称为序列)。允许重复的元素。
    允许多个 null 元素
Set接口:一个不包含重复元素的 collection,最多包含一个 null 元素
Queue接口:对列,以先进先出的方式排序各个元素


二、List接口
(1)ArrayList实现类
List list = new ArrayList();
ArrayList list = new ArrayList(); --android开发中使用子类比父类效率高


* 实现原理:使用动态对象数组,默认初始化一个空数组,
* 在第一次添加元素时,动态扩充为容量10的对象数组
* 第二次容量满后的扩充算法是:原来数组长度+原来数组长度/2
* 数组不适合插入,删除操作
* 在集合中,最好存储相同类型的数据,避免类型不一致在使用时的类型转换问题
* 如何在集合中确保存储同一种数据类型?使用泛型
* 为了防止数组动态扩充的次数过多,建议一创建ArrayList时,给定初始容量大小
     * 线程不安全,适合在单线程访问时使用,在多线程访问时,
     * 可以通过集合工具类重新构造一个线程安全的ArrayList
* 在jdk1.2开始
*/
(2)Vector实现类
Vector v = new Vector();
* 实现原理:向量,基于动态对象数组,默认数组大小为10,
* 动态扩充的算法:如果给Vector构造时设置了增量,
* 那么每次扩充的大小为:原来大小+增量;
* 如果增量为0(默认为0),那么每次扩充的大小为:原来大小的2倍
* 在JDK1.0版本开始,在1.2后重新实现List接口
* Vector是线程安全的,在多线程并发访问时可以保正数据安全,
* 但在单线程访问时,效率比
* ArrayList低。
* 为 避免扩充次数,可以在构造Vector时给定初始容量


(3)LinkedList实现类
    实现原理:基于链表数据结构,适合插入删除操作。


    使用LinkedList 作为链表结构使用
    LinkedList link = new LinkedList();
    link.add("lily");


    使用LinkedList作为队列使用(先进先出)
        //队列
String s1 = list.peek();//获取队列的头元素
System.out.println("peek="+s1);
String s2 = list.poll();
System.out.println("poll="+s2);//获取并移除头元素
System.out.println(list);
System.out.println("--------------");


    使用 LinkedList作为栈使用(先进后出)
        list.push("hanmeimei");//压栈
list.push("lilei");
list.push("lucy");
System.out.println(list);
String s3 = list.pop();//出栈
System.out.println(s3);


三、Set接口
不允许重复元素,允许一个 NULL 值,无序,并不保正顺序永久不变
检查对象是否重复,通过比较两个元素的equals是否相等。


(1)HashSet实现类
    基于HashMap的实现(哈希表数据结构(数组+链表)),可以实现大数据量的
    快速查找。
    HashSet<String> set = new HashSet<>();
    set.add("lucy");
    set.add("lilei");


重复的元素无法添加到集合中,那自定义对象如何检查是否是同一个:使用equals方法


需求:
在程序中如果我们想把同类型的不同的两个对象,但这两个对象的属性完全相同,我们
要认为这两个对象是同一个对象时,就需要重写hashCode和equals方法。
两个对象的equals方法相同,那么要求两个对象的hashCode必须相同,
两个对象的equals方法不相同,不要求两个对象的hashCode一定不同。


hashCode的作用
hashCode(),是Object类中定义的方法,目的是用于把对象保存在哈希表数据结构中
用于计算使用。


在哈希表数据结构中,如何检查对象是否重复呢?
先调用对象hashCode方法,比较此hashCode是否在集合中存在,如果不存在,则添加
成功,表示此对象不重复;如果存在hashCode相同的对象,那么再调用equals方法来
判断对象是否相等,如果相等,表示重复,如果不相等则添加成功。


(2)TreeSet实现类
提供一种可排序的Set集合,基于TreeMap实现(二叉树中的红黑树),TreeSet中的
排序是基于Comparable接口来实现的,所以,在把自定义类型存储到 TreeSet中时,
必须实现 Comparable接口,来实现对象之间的比较,并且会利用Comparable来实现
对象是否重复。


package com.moliying.vince;


public class Dog implements Comparable<Dog> {


private String name;
private int id;


@Override
public String toString() {
return "Dog [name=" + name + ", id=" + id + "]";
}


public Dog() {}


public Dog(String name, int id) {
super();
this.name = name;
this.id = id;
}
    //getter and setter...
@Override
public int compareTo(Dog o) {
return this.id - o.id;
}
}


TreeSet<Dog> tree = new TreeSet<Dog>();
tree.add(new Dog("wangwang",1));
tree.add(new Dog("wangcai",2));
tree.add(new Dog("herry",3));
System.out.println(tree);


(3)LinkedHashSet实现类
是HashSet 的子类,使用链表来维护添加顺序的一个哈希表实现,来解决排序问题


LinkedHashSet<Cat> link = new LinkedHashSet<Cat>();
Cat cat1 = new Cat("miaomiao",5,1);
Cat cat2 = new Cat("huahua",3,2);
Cat cat3 = new Cat("tom",5,3);
Cat cat4 = new Cat("miaomiao",5,1);
link.add(cat1);
link.add(cat2);
link.add(cat3);
link.add(cat4);
System.out.println(link);


小结:Set接口的实现,都使用基于 Map(Mapping)实现类,其HashSet使用率最高
在存储单个对象时,适合存储大数据量,查询速度快。


四、Iterator接口
此接口用于实现集合的迭代,在Collection接口中定义了iterator方法,此方法由具体的
子类实现,这样的好处是,对于集合我们可以有统一的迭代方法。


比如:
private static void print(Collection<Dog> c){


Iterator<Dog> iter = c.iterator();
while(iter.hasNext()){
Dog d = iter.next();
System.out.println(d);
}
}




五、Map接口
此接口用于存储两个对象,一个作为key,一个作为value,要求key不能重复,否则
将把已存在的key覆盖


(1)HashMap
基于哈希表数据结构实现(数组+链表),在首次添加元素时默认数组大小为16,加载
因子为0.75,添加元素时,通过计算key对象的hash值对数组大小取余,来决定元素要
存储在数组中的哪个位置,当该位置已有元素存在,那么以链表结构存储。根据元素
删除和查找同理。使用哈希表来存储大数据量,有助于提高添加和查询的效率。但要注意
的是,当哈希表的存储空间达到加载因子的比例时,需要动态扩充数组,算法是原来大小
的两倍扩充,此时,原来的所有元素,需要重新计算hash值来重新分布到新数组中存储
,这样频繁的扩充会影响性能,数据量越大,性能越低。所以我们在使用hash表时,要
充分考虑扩充的次数,通过我们建议在构造hashMap时,可以指定合理的容量大小,来
避免扩充带来的性能问题。


HashMap的迭代方式:


private static void hashMap(){
HashMap<Integer,String> map = new HashMap<>();
map.put(1, "黄笙");
map.put(2, "石林");
map.put(3, "建达");
map.put(4, "文哲");


System.out.println(map.get(1));
System.out.println(Integer.hashCode(4));


//System.out.println(Integer.hashCode(200)^(Integer.hashCode(200)>>>3));
Integer i = new Integer(1);


//迭代values
Collection<String> coll = map.values();
for(String value: coll){
System.out.println(value);
}
System.out.println("-----------------");
//迭代keys(常用 )
Set<Integer> keys = map.keySet();
for(Integer key: keys){
String value = map.get(key);
System.out.println(key+"->"+value);
}
System.out.println("--------------------");
//迭代entry(map内部用于存储一个键值对的对象)
Set<Entry<Integer,String>> entrys = map.entrySet();
for(Entry entry: entrys){
System.out.println(entry.getKey()+"->"+entry.getValue());
}
}




(2)Hashtable
与 HashMap相似,基于哈希表实现,默认初始容量为11,加载因子0.75,动态扩
充算法是:原来数组长度*2+1,与HashMap的最大区别是Hashtable是线程安全的
HashMap是线程不安全的。Hashtable从 JDK1.0开始


(3)TreeMap
基于二叉树的平衡红黑树实现,可以实现自然顺序排列,线程不安全
TreeMap<String,String> tree = new TreeMap<String,String>();
tree.put("one", "老黄");
tree.put("two", "老白干");
tree.put("three", "小达");
tree.put("four", "小马过河");


当 key为自定义对象时,该对象类型必须实现Comparable来比较对象的排列顺序,
并且用于检查重复值。
TreeMap<Cat,String> map = new TreeMap<>();
map.put(new Cat("黄猫",19,1), "黄");
map.put(new Cat("黑猫",23,2), "黑");
map.put(new Cat("白猫",19,3), "白");


Cat类的定义:


public class Cat implements Comparable<Cat>{}


(4)LinkedHashMap
哈希表和链接列表实现,具有可预知的迭代顺序。
此实现与 HashMap 的不同之处在于,
后者维护着一个运行于所有条目的双重链接列表。
此链接列表定义了迭代顺序,
该迭代顺序通常就是将键插入到映射中的顺序(插入顺序)。
注意,如果在映射中重新插入 键,则插入顺序不受影响。
(如果在调用 m.put(k, v) 前 m.containsKey(k) 返回了 true,
则调用时会将键 k 重新插入到映射 m 中。)


六、Collections工具类
用于操作集合的工具类,可以实现构造线程安全的List,Map,Set集合,集合的排序
求最大值最小值,二分查找等功能。


面试题:
(1)ArrayList与Vector的区别
(2)HashMap与 Hashtable的区别
(3)Collection与 Collections的区别
(4)hashCode的作用
(5)JAVA 中有内存泄露吗,举例说明


七、小结


                    List(ArrayList、LinkedList、Vector、Stack)
Collection
                    Set(HashSet、TreeSet、LinkedHashSet)


Map    (HashMap、TreeMap、Hashtable、LinkedHashMap)




Collection:存一个对象
Map:存两个对象


 Iterator:迭代器接口,用于统一集合的遍历


常用数据结构:
数组、链表、二叉树、哈希表、栈、队列


--------------------------------------------------------
--                                                                            --
--                      XXX超市管理系统                           --
--                                                                            --
--------------------------------------------------------
1、欢迎进入 XXX 超市管理系统
        特点:


1、登录    2、注册
请选择:
1
请输入用户名:
请输入密码:


2
请输入新用户名:
请设置新密码:
请再次输入密码:


注册成功(写入文件)


登录成功!
------功能列表--------
1、购买    2、进货    3、订单查询  4、商品列表  5、退出


请选择:
购买界面


显示商品详细信息
1 白菜  2元/斤                  2、黄瓜
3、胡萝卜                       4、花生米
5、矿泉水                       6、啤酒
7、内裤                            8、卫生纸
9、拖鞋                            10、被子
11、袜子                           12、薯片
13、圆珠笔                      14、口香糖
15、香烟                           16、方便面
17、牛肉干                      18、面包
19、香肠                           20、苹果
21、榴莲
0、结束
请输入产品编号:
请输入数量:


生成订单保存到文件




2、进货界面
请输入商品名称:
请输入商品数量:
请输入商品价格:
请输入商品单位:


OK,添加成功!


3、订单查询
查询出所有订单列表


4、商品列表
商品名称    商品数量    商品单价    商品单位


(修改、删除)


5、退出




技术要求:
(1)文件操作
(2)国际化
(3)集合
(4)设计模式

0 0