概念
◼
集合(Set)的特点
不存放重复的元素
常用于去重
✓
存放新增 IP,统计新增 IP 量
✓
存放词汇,统计词汇量
✓
.....
◼
思考:集合的内部实现能否直接利用以前学过的数据结构?
动态数组
链表
二叉搜索树(AVL树、红黑树)
接口
public interface Set<E> {
int size();
boolean isEmpty();
void claer();
boolean contains(E element);
void add(E element);
void remove(E element);
void traversal(Visitor<E> visitor);
public static abstract class Visitor<E>{ // 访问器
boolean stop;
public abstract boolean visit(E element);
}
}
链表实现集合
双向链表实现相应的集合过程。
/**
* LinkedList实现的ListSet
*/
public class ListSet<E> implements Set<E>{
private LinkedList<E> list = new LinkedList<>();
public int size() {
return list.size();
}
public boolean isEmpty() {
return list.isEmpty();
}
public void clear() {
list.clear();
}
public boolean contains(E element) {
return list.contains(element);
}
public void add(E element) {
// if(list.contains(element)) return;
int index = list.indexOf(element);
if(index == List.ELEMENT_NOT_FOUND){ // 没有该元素
list.add(element); // 没有就添加
}else{
list.set(index, element); // 已经有就替换
}
}
public void remove(E element) {
int index = list.indexOf(element);
if(index != List.ELEMENT_NOT_FOUND){
list.remove(index);
}
}
public void traversal(Visitor<E> visitor) {
int size = list.size();
for(int i = 0; i < size; i++){
visitor.visit(list.get(i));
}
}
}
红黑树实现集合
/**
* 红黑树实现集合
*/
public class TreeSet<E> implements Set<E>{
private RBTree<E> tree = new RBTree<>();
public int size() {
return tree.size();
}
public boolean isEmpty() {
return tree.isEmpty();
}
public void claer() {
tree.clear();
}
public boolean contains(E element) {
return tree.contains(element);
}
public void add(E element) {
tree.add(element);
}
public void remove(E element) {
tree.remove(element);
}
public void traversal(Visitor<E> visitor) {
tree.inorder(new BinaryTree.Visitor<E>() {//
@Override
public boolean visit(E element) {
return visitor.visit(element);
}
});
}
}
复杂度和性能的角度进行分析
复杂度:链表O(n) 红黑树O(log(n))
性能分析红黑树是很强大的,实现一个功能的查询与去重是非常快的------二叉搜索树是天然的去重的。
TreeSet的局限性
红黑树必需具备可比较性,如果要是使用TreeSet的话,最好传递一个comparator,也可以使用原来的默认方法.如果要是不是使用可比较性的,可以使用Hash表,后面进行讲解.