Set接口之HashSet、TreeSet、EnumSet
2014-12-11 10:08
351 查看
Set接口:与collection基本上完全一样,它没有提供任何额外的方法,实际上set就是collection,只是行为不同(set不允许包含重复元素)。
一、HashSet
HashSet是Set接口的典型实现,HashSet按hash算法来存储元素,因此具有很好的存取和查找性能。它具有以下特点:
1、不能保证元素的排列顺序,顺序有可能发生变化。
2、HashSet是异步的。
3、集合元素值可以是null。
4、当向HashSet集合中存入一个元素时,HashSet会调用该对象的hashCode()方法来得到该对象的hashCode值,然后根据该HashCode值来确定该对象在HashSet中存储的位置。
HashSet还有一个子类LinkedHashSet,其集合也是根据元素hashCode值来决定元素的存储位置,但它同时用链表来维护元素的次序,这样使得元素看起来是以插入的顺序保存的,也就是说,当遍历LinkedHashSet集合元素时,它将会按元素的添加顺序来访问集合里的元素。所以LinkedHashSet的性能略低于HashSet,但在迭代访问全部元素时将有很好的性能,因为它以链表来维护内部顺序。
二、TreeSet
TreeSet是SortSet接口的唯一实现,TreeSet可以确保集合元素处于排序状态。与HashSet相比,TreeSet还提供了几个额外的方法:
1、Comparator comparator():返回当前set使用的Comparator,或者返回null,表示以自然方式排序。
2、Object first():返回集合中的第一个元素。
3、Object last():返回集合中的最后一个元素。
4、Object lower(Object e):返回集合中位于指定元素之前的一个元素。
5、Object higher(Object e):返回集合中位于指定元素之后的一个元素。
6、SortedSet subSet(from Element,to Element):返回此set的子集合,范围从from Element到to Element(闭包)。
7、SortedSet headSet(toElement):返回此Set的子集,由小于toElement的元素组成。
8、SortedSet tailSet(fromElement):返回此Set的子集,由大于等于fromElement的元素组成。
public static void main(String[] args) {
TreeSet num=new TreeSet();
num.add(5);
num.add(2);
num.add(10);
num.add(-9);
System.out.println(num); //输出:[-9,2,5,10]集合元素已经处于排序状态
System.out.println(num.first()); //输出-9
System.out.println(num.last()); //输出10);
System.out.println(num.headSet(4)); //输出-9,2返回小于4的子集
System.out.println(num.tailSet(5)); //输出5,10返回大于等于5的子集
System.out.println(num.subSet(-9,5)); //输出-9,2返回大于等于-9小于5的子集
}
根据上面程序可以看出,TreeSet不是根据元素插入顺序进行排序的,而是根据元素的值来排序的。TreeSet支持两种排序方法:自然排序和定制排序。
1、自然排序:TreeSet会调用集合元素的compareTo(Object obj)方法来计较元素之间大小关系,然后将集合元素按升序排列。如果试图把一个对象加进TreeSet时,则该对象的类必须实现Comparable接口,否则程序将会出现ClassCastException异常。
2、定制排序:如果需要实现定制排序,则可以使用Compa接口的帮助,该接口包含一个int compare(o1,o2)方法,该方法用于计较两个数的大小,如果返回正整数,则表明o1>o2;如果返回0,则表明o1=o2;如果返回负整数,则表明o1<02。
注意:不可以向TreeSet中添加类型不同的对象,否则会引起ClassCastException异常。
三、EnumSet
1、EnumSet中所有值都必须是指定枚举类型的值,它的元素也是有序的,以枚举值在枚举类的定义顺序来决定集合元素的顺序。
2、EnumSet集合不允许加入null元素,否则会抛出NullPointerException异常。
3、EnumSet类没有暴露任何构造器来创建该类的实例,程序应该通过它提供的static方法来创建EnumSet对象,常用的static方法如下:
static EnumSet allOf(Class elementType):创建一个包含指定枚举类里所有枚举值的EnumSet集合。
static EnumSet complementOf(EnumSet s):创建一个其元素类型与指定EnumSet里元素类型相同的EnumSet,新的EnumSet集合包含原EnumSet集合所不包含的、此枚举类剩下的枚举值。
static EnumSet copyOf(collection c):使用一个普通集合来创建EnumSet集合。
static EnumSet copyOf(EnumSet e):创建一个与指定EnumSet具有相同元素类型、相同集合元素的EnumSet。
static EnumSet noneOf(Class elementType):创建一个元素类型为指定枚举类型的空EnumSet.
static EnumSet of(E first,E...rest):创建一个包含一个或多个枚举值的EnumSet,传入的多个枚举值必须属于同一个枚举类。
static EnumSet range(E from,E to):创建包含从from枚举值,到to枚举值范围内所有枚举值的EnumSet集合。
public static void main(String[] args) {
EnumSet e1=EnumSet.allOf(Season1.class); //创建一个EnumSet集合,集合元素就是Season里的全部枚举值
System.out.println(e1); //输出[SPRING, SUMMER, FALL, WINTER]
EnumSet e2=EnumSet.noneOf(Season1.class); //创建一个EnumSet空集合,指定其集合元素是season1的枚举值
e2.add(Season1.WINTER);
e2.add(Season1.SPRING);
System.out.println(e2); //输出[SPRING, WINTER]
EnumSet e3=EnumSet.of(Season1.SUMMER, Season1.WINTER); //以指定枚举值创建EnumSet集合
System.out.println(e3); //输出[SUMMER, WINTER]
EnumSet e4=EnumSet.range(Season1.SUMMER, Season1.WINTER);
System.out.println(e4); //输出[SUMMER, FALL, WINTER]
EnumSet e5=EnumSet.complementOf(e4);
System.out.println(e5); //输出[SPRING]
}
总结:
1、HashSet的性能比Treeset好,因为TreeSet需要额外的红黑树算法来维护集合元素的次序,只有当需要一个保持排序的Set时,才会用TreeSet。
2、EnumSet是性能最好的,但它只能保存枚举值。
3、它们都是线程不安全的。
一、HashSet
HashSet是Set接口的典型实现,HashSet按hash算法来存储元素,因此具有很好的存取和查找性能。它具有以下特点:
1、不能保证元素的排列顺序,顺序有可能发生变化。
2、HashSet是异步的。
3、集合元素值可以是null。
4、当向HashSet集合中存入一个元素时,HashSet会调用该对象的hashCode()方法来得到该对象的hashCode值,然后根据该HashCode值来确定该对象在HashSet中存储的位置。
HashSet还有一个子类LinkedHashSet,其集合也是根据元素hashCode值来决定元素的存储位置,但它同时用链表来维护元素的次序,这样使得元素看起来是以插入的顺序保存的,也就是说,当遍历LinkedHashSet集合元素时,它将会按元素的添加顺序来访问集合里的元素。所以LinkedHashSet的性能略低于HashSet,但在迭代访问全部元素时将有很好的性能,因为它以链表来维护内部顺序。
二、TreeSet
TreeSet是SortSet接口的唯一实现,TreeSet可以确保集合元素处于排序状态。与HashSet相比,TreeSet还提供了几个额外的方法:
1、Comparator comparator():返回当前set使用的Comparator,或者返回null,表示以自然方式排序。
2、Object first():返回集合中的第一个元素。
3、Object last():返回集合中的最后一个元素。
4、Object lower(Object e):返回集合中位于指定元素之前的一个元素。
5、Object higher(Object e):返回集合中位于指定元素之后的一个元素。
6、SortedSet subSet(from Element,to Element):返回此set的子集合,范围从from Element到to Element(闭包)。
7、SortedSet headSet(toElement):返回此Set的子集,由小于toElement的元素组成。
8、SortedSet tailSet(fromElement):返回此Set的子集,由大于等于fromElement的元素组成。
public static void main(String[] args) {
TreeSet num=new TreeSet();
num.add(5);
num.add(2);
num.add(10);
num.add(-9);
System.out.println(num); //输出:[-9,2,5,10]集合元素已经处于排序状态
System.out.println(num.first()); //输出-9
System.out.println(num.last()); //输出10);
System.out.println(num.headSet(4)); //输出-9,2返回小于4的子集
System.out.println(num.tailSet(5)); //输出5,10返回大于等于5的子集
System.out.println(num.subSet(-9,5)); //输出-9,2返回大于等于-9小于5的子集
}
根据上面程序可以看出,TreeSet不是根据元素插入顺序进行排序的,而是根据元素的值来排序的。TreeSet支持两种排序方法:自然排序和定制排序。
1、自然排序:TreeSet会调用集合元素的compareTo(Object obj)方法来计较元素之间大小关系,然后将集合元素按升序排列。如果试图把一个对象加进TreeSet时,则该对象的类必须实现Comparable接口,否则程序将会出现ClassCastException异常。
2、定制排序:如果需要实现定制排序,则可以使用Compa接口的帮助,该接口包含一个int compare(o1,o2)方法,该方法用于计较两个数的大小,如果返回正整数,则表明o1>o2;如果返回0,则表明o1=o2;如果返回负整数,则表明o1<02。
注意:不可以向TreeSet中添加类型不同的对象,否则会引起ClassCastException异常。
三、EnumSet
1、EnumSet中所有值都必须是指定枚举类型的值,它的元素也是有序的,以枚举值在枚举类的定义顺序来决定集合元素的顺序。
2、EnumSet集合不允许加入null元素,否则会抛出NullPointerException异常。
3、EnumSet类没有暴露任何构造器来创建该类的实例,程序应该通过它提供的static方法来创建EnumSet对象,常用的static方法如下:
static EnumSet allOf(Class elementType):创建一个包含指定枚举类里所有枚举值的EnumSet集合。
static EnumSet complementOf(EnumSet s):创建一个其元素类型与指定EnumSet里元素类型相同的EnumSet,新的EnumSet集合包含原EnumSet集合所不包含的、此枚举类剩下的枚举值。
static EnumSet copyOf(collection c):使用一个普通集合来创建EnumSet集合。
static EnumSet copyOf(EnumSet e):创建一个与指定EnumSet具有相同元素类型、相同集合元素的EnumSet。
static EnumSet noneOf(Class elementType):创建一个元素类型为指定枚举类型的空EnumSet.
static EnumSet of(E first,E...rest):创建一个包含一个或多个枚举值的EnumSet,传入的多个枚举值必须属于同一个枚举类。
static EnumSet range(E from,E to):创建包含从from枚举值,到to枚举值范围内所有枚举值的EnumSet集合。
public static void main(String[] args) {
EnumSet e1=EnumSet.allOf(Season1.class); //创建一个EnumSet集合,集合元素就是Season里的全部枚举值
System.out.println(e1); //输出[SPRING, SUMMER, FALL, WINTER]
EnumSet e2=EnumSet.noneOf(Season1.class); //创建一个EnumSet空集合,指定其集合元素是season1的枚举值
e2.add(Season1.WINTER);
e2.add(Season1.SPRING);
System.out.println(e2); //输出[SPRING, WINTER]
EnumSet e3=EnumSet.of(Season1.SUMMER, Season1.WINTER); //以指定枚举值创建EnumSet集合
System.out.println(e3); //输出[SUMMER, WINTER]
EnumSet e4=EnumSet.range(Season1.SUMMER, Season1.WINTER);
System.out.println(e4); //输出[SUMMER, FALL, WINTER]
EnumSet e5=EnumSet.complementOf(e4);
System.out.println(e5); //输出[SPRING]
}
总结:
1、HashSet的性能比Treeset好,因为TreeSet需要额外的红黑树算法来维护集合元素的次序,只有当需要一个保持排序的Set时,才会用TreeSet。
2、EnumSet是性能最好的,但它只能保存枚举值。
3、它们都是线程不安全的。
相关文章推荐
- java(20130802)Set:HashSet TreeSet、Map(接口):HashTable Hashmap、比较list set map
- Set接口——HashSet和TreeSet
- Set接口下的 HashSet, LinkedHashSet, TreeSet
- set集合 HashSet: TreeSet实现Comparable接口,覆盖compareTo方法。 类实现Comparator接口,覆盖compare方法。
- JavaSE入门学习36:Java集合框架之Set接口及其实现类HashSet和TreeSet
- 小东吖 之 java Set接口 HashSet集合 TreeSet集合
- Java类集--Set接口、HashSet、TreeSet、SortedSet接口
- Set接口的实现类HashSet和TreeSet的区别
- Java中的集合HashSet、LinkedHashSet、TreeSet和EnumSet(二)
- Set接口(Set接口简介、HashSet集合、TreeSet集合 )
- Set接口之HashSet、TreeSet、EnumSet
- Thinking in Java之Set接口、HashSet源码学习
- java集合类,List和Set比较,各自的子类比较(ArrayList,Vector,LinkedList;HashSet,TreeSet),Map集合比较
- 【Java】常见的Set类型,HashSet、TreeSet、LinkedHashSet
- Set集合HashSet,TreeSet
- 小小的总结一下java异常处理和List、ArrayList、Vector、Set、HashSet、TreeSet集合的简单应用
- 17 API-集合(登录注册案例集合版,Set集合(Set_HashSet_TreeSet),Collection单列集合总结)
- Java基础-17总结,登录注册案例,Set集合,HashSet,TreeSet,LinkHashSet
- Set接口详解——TreeSet
- Java集合Set、Map、HashSet、HashMap、TreeSet、TreeMap等