目录
- vector的特点
- LinkedList底层结构
- 模拟双向链表
- 比较ArrayList和LinkedList
- Set接口
- 基本介绍
- Set接口的遍历方式
- Set接口实现类对象的特点
- Set接口实现类HashSet
- 模拟HashSet/HashMap的底层结构
vector的特点
- Vector底层是一个对象数组
- Vector是线程同步的,即线程安全的,Vector类的操作方法带有synchronize(带锁也就意味着效率有所降低)
LinkedList底层结构
- LinkedList底层实现了双向链表和双端队列
- 可以添加任意元素(元素可以重复),包括null
- 线程不安全,没有实现同步
- LinkedList中维护了两个属性first和last,分别指向首结点和尾结点
- 每个节点(Node对象)里面又维护了prev、next、item三个属性,其中通过prev指向前一个结点,通过next指向后一个结点。最终实现双向链表
模拟双向链表
package cs.kaoyan.javase.com.list7;
public class Test4 {
public static void main(String[] args) {
Node zs = new Node("zhang san");
Node ls = new Node("li si");
Node ww = new Node("wang wu");
//zs -> ls -> ww
zs.next = ls;
ls.next = ww;
//zs <- ls <- ww
ww.prev = ls;
ls.prev = zs;
//设置头结点
Node first = zs;
//设置尾结点
Node last = ww;
//从头到尾遍历双向链表
//zhang san -> li si -> wang wu
//一般不直接对头结点进行操作
Node temp1 = first;
while (true){
if (temp1 == null){
//遍历结束
break;
}
System.out.println(temp1.item);
temp1 = temp1.next;
}
System.out.println("-------------");
//从尾往头遍历
//wang wu -> li si -> zhang san
Node temp2 = last;
while (true){
if (temp2 == null){
//遍历结束
break;
}
System.out.println(temp2.item);
temp2 = temp2.prev;
}
//模拟插入操作
//zhang san -> li si -> zhao liu -> wang wu
Node zl = new Node("zhao liu");
zl.next = ww;
zl.prev = ls;
ls.next = zl;
ww.prev = zl;
System.out.println("-------------");
//再次从头到尾遍历
//zhang san -> li si -> zhao liu -> wang wu
Node temp3 = first;
while (true){
if (temp3 == null){
//遍历结束
break;
}
System.out.println(temp3.item);
temp3 = temp3.next;
}
}
}
class Node{
public Object item;//存放数据
public Node prev;//指向前一个结点
public Node next;//指向后一个结点
//单参构造方法
public Node(Object item) {
this.item = item;
}
}
比较ArrayList和LinkedList
- 如果我们改查的操作多,选择ArrayList(底层结构决定改查的效率)
- 如果我们增删的操作多,选择LinkedList3
- 一般来说,在程序中,80% ~ 90%都是查询,因此大部分情况下会选择ArrayList
- 在一个项目中,根据业务灵活选择,可以一个模块使用的是ArrayList,另外一个模块是LinkedList
Set接口
基本介绍
- 无序(添加和取出的顺序不一致)
- 没有索引不允许重复元素
- 最多包含一个null(不允许元素重复)
- 和List接口一样,Set接口也是Collection的子接口,因此常用方法和Collection接口一样
Set接口的遍历方式
同Collection的遍历方式一样,因为Set接口是Collection接口的子接口
- 可以使用迭代器遍历
- 增强for遍历
- 不能使用索引的方式来遍历
Set接口实现类对象的特点
- Set接口的实现类的对象(Set接口对象),不能存放重复的元素,可以添加一个null
- Set接口对象存放数据是无序(即添加的顺序和取出的顺序不一致)
- 取出的顺序虽然不是添加的顺序,但是他的固定,在元素固定的时候不会改变
- 总结:无序且唯一
package cs.kaoyan.javase.com.set;
import java.util.HashSet;
public class Test {
public static void main(String[] args) {
HashSet set = new HashSet();
set.add("zhang san");
set.add("li si");
set.add("wang wu");
set.add("wang wu");
set.add("zhao liu");
set.add("zhao liu");
set.add(null);
for (int i = 0; i < 10; i++) {
System.out.println(set);
}
/*
[null, wang wu, zhang san, li si, zhao liu]
[null, wang wu, zhang san, li si, zhao liu]
[null, wang wu, zhang san, li si, zhao liu]
[null, wang wu, zhang san, li si, zhao liu]
[null, wang wu, zhang san, li si, zhao liu]
[null, wang wu, zhang san, li si, zhao liu]
[null, wang wu, zhang san, li si, zhao liu]
[null, wang wu, zhang san, li si, zhao liu]
[null, wang wu, zhang san, li si, zhao liu]
[null, wang wu, zhang san, li si, zhao liu]*/
}
}
Set接口实现类HashSet
- HashSet实现了Set接口
- HashSet实际上是HashMap
public HashSet() {
map = new HashMap<>();
}
- 可以存放null值,但是只能有一个null
- HashSet不保证元素是有序的
- 不能有重复元素
模拟HashSet/HashMap的底层结构
package cs.kaoyan.javase.com.set;
/**
* 模拟HashSet/HashMap的底层结构
*/
public class Test2 {
public static void main(String[] args) {
//创建一个数组,类型是Node
Node[] table = new Node[5];
//新建一个"张三"结点
Node zs = new Node("zhang san", null);
//数组下标为1的位置指向张三
table[1] = zs;
Node ls = new Node("li si", null);
zs.next = ls;
Node ww = new Node("wang wu", null);
ls.next = ww;
Node zl = new Node("zhao liu", null);
ww.next = zl;
}
}
class Node{
Object item;//存放数据
Node next;//指向下一个结点
//构造器
public Node(Object item, Node next) {
this.item = item;
this.next = next;
}
}