java - 集合 - set

collection分类:

list:有序可重复

set:无序不重复

 

HashSet

底层是Hashmap存储,每次容量使用到达75%时扩容

hash:散列表结构(数组+链表)

 

package set;

import stringtest.TestClass;

import java.util.ArrayList;
import java.util.HashSet;
import java.util.Iterator;

public class HashSetTest {
    public static void main(String[] args){
        HashSet<String> set = new HashSet<String>();

        set.add("b");//添加
        set.add("C");
        set.add("a");
        set.add("A");
        set.add("c");

        System.out.println(set);
        //[a, A, b, C, c]
        //list:有序可重复
        //set:无序不重复
        // set:顺序与存入顺序不一致,内部存储顺序根据hashcode计算获得
        ArrayList<String> a = new ArrayList<String>();
        a.add("d");
        a.add("d");
        a.add("E");
        a.add("f");
        a.add("e");
        a.add("D");
        a.add("F");
        System.out.println(a);
        //[d, d, E, f, e, D, F]  list:有序可重复,保持了存入顺序,可以有重复数据
        set.addAll(a);//存入集合
        System.out.println(set);
        //[a, A, b, C, c, d, D, e, E, f, F] set:无序不重复:集合顺序会被打乱,而且set中不会出现重复的数据(可以用来去重或者排序?)

        System.out.println(set.remove("b"));//删除元素,因为是无序的所以没有根据index删除
        System.out.println(set.remove("b"));//返回的是boolean型,没有该元素返回false
        System.out.println(set);
        //[a, A, C, c, d, D, e, E, f, F]

        //遍历:
        //1.5之后可以使用增强for循环遍历
        for(String s: set){
            System.out.print(s + " ");//没有index所以不能用for循环遍历,但是可以用增强for循环(foreach)遍历
        }
        System.out.println();
        //a A C c d D e E f F
        //1.5之前需要使用迭代器,Iterator
        Iterator<String> it = set.iterator();
        while(it.hasNext()){ //判断之后是否有元素
            System.out.print(it.next() + " "); //把下一个取出来返回
        }
        System.out.println();
        //a A C c d D e E f F

        //无重复原则实现:
        HashSet hashSet = new HashSet();
        hashSet.add("aaa");
        hashSet.add("aaa");
        hashSet.add("aaa");
        hashSet.add(new String("bbb"));
        hashSet.add(new String("bbb"));
        hashSet.add(new String("bbb"));
        hashSet.add(new TestClass("ccc"));
        hashSet.add(new TestClass("ccc"));
        hashSet.add(new TestClass("ccc"));
        System.out.println(hashSet);
        //[aaa, stringtest.TestClass@5594a1b5, bbb, stringtest.TestClass@3ac3fd8b, stringtest.TestClass@43a25848]
        //String只保存了一个,new String也只保持了一个(说明底层判断重复不是单纯的比较地址
        //但是引用类型数据内容相同会全部保留
        //原因: String重写了equals方法,比较时使用的是equals,比较的是hashcode
        //如果重写TestClass的equals和hashcode,则可以只保留一个。

        //equals中:之前equals比较除了String,底层都是用的 == , tc instanceof TestClass判断比较的是不是TestClass,是的话用String的equals比较TestClass中的String s是否相等
        //hashCode()中: 之前是返回地址的hashcode,现在改为返回对象中 s 的hashcode
        //直接把下面的代码加入TestClass中,可以覆盖掉Object的同名同参数同返回值方法 -- 方法重写
//        public boolean equals(Object tc){
//            if(tc instanceof TestClass && ((TestClass) tc).s.equals(this.s)){
//                return true;
//            }
//            return false;
//        }
//
//        public int hashCode(){
//            return this.s.hashCode();
//        }

        //重写TestClass后返回
        //[aaa, stringtest.TestClass@18003, bbb]

    }
}

 

TreeSet:

也是set的一种,结构是二叉树

常用方法和HashSet基本一样

比较使用了compareTo

有一定顺序,可以用来排序

posted @ 2019-10-07 12:43  不咬人的兔子  阅读(176)  评论(0编辑  收藏  举报