20151118 Set集合+HashSet类+TreeSet类

Set集合为集类型,集是最简单的一种集合,存放于集合中的对象不按特定方式排序,只是简单的把对象加入集合中,类似于向口袋里放东西。

1. HashSet类
  • 由HashSet类实现的Set集合的优点是能够快速定位集合中的元素。
  • 由HashSet类实现的Set集合中的对象必须是唯一的,所以需要添加到由HashSet类实现的Set集合中的对象,需要重新实现equals()方法。
  • 由HashSet类实现的Set集合按照哈希码排序,根据对象的哈希码确定对象的存储位置,所有需要添加到由HashSet类实现的Set集合中的对象,还需要重新实现hashCode()方法。从而保证插入集合中的对象能够合理分布在集合中,以便于快速定位集合中的对象。
    【例】使用HashSet类。创建一个Person类,该类需要重新实现equals(Object obj)方法和hashCode()方法,以保证对象标识的唯一性和存储分布的合理性。
    代码如下:

    import java.util.Set;
    import java.util.HashSet;
    import java.util.Iterator;
    
    public class testHashSet {
        public static void main(String[] args){
            Set<Person> hashSet = new HashSet<Person>();
            Person person1 = new Person("马先生", 220181);
            Person person2 = new Person("李先生", 220186);
            Person person3 = new Person("王小姐", 220193);
            hashSet.add(person1);
            hashSet.add(person2);
            hashSet.add(person3);
    
            Iterator<Person> it = hashSet.iterator();
            while(it.hasNext()){
            Person person = it.next();
            System.out.println(person.getName() + "   " + person.getId_card());
            }
        }
    }
    
    class Person{
        private String name;
        private long id_card;
    
        public Person(String name, long id_card){
            this.name = name;
            this.id_card = id_card;
        }
    
        public String getName(){
            return this.name;
        }
        public long getId_card(){
            return this.id_card;
        }
        public void setName(String name){
            this.name = name;
        }
        public void setId_card(long id_card){
            this.id_card = id_card;
        }
    
        public int hashCode(){
            final int PRIME = 31;
            int result = 1;
            result = result * PRIME + (int)(this.id_card ^ (this.id_card >>> 32));
            result = result * PRIME + (int)((this.name == null) ? 0 : name.hashCode());
            return result;
        }
    
        public boolean equals(Object obj){
            if(this == obj)
                return true;
            if(null == obj)
                return false;
            if(this.getClass() != obj.getClass())
                return false;
            final Person other = (Person)obj;
            if(this.id_card != other.id_card)
                return false;
            if(null == this.name){
                if(null != other.name)
                    return false;
            }else if(!this.name.equals(other.name)){
                return false;
            }
            return true;
        }
    }
    

    运行截图如下:
    运行截图

如果既想保留HashSet类快速定位集合中对象的优点,又想让集合中的对象按插入的顺序保存,可以通过HashSet类的子类LinkedHashSet实现Set集合。即将Person类中的如下代码:

Set< Person > hashSet = new HashSet< Person >();

替换为如下代码:

Set< Person > hashSet = new LinkedHashSet< Person >(); 
2. TreeSet类

TreeSet类不仅实现了Set接口,还实现了java.util.SortedSet接口,从而保证了在遍历集合时按照递增的顺序获得对象。

  • 如果遍历对象时按照自然顺序递增排列,则由TreeSet类实现的Set集合存入的对象必须实现Comparable接口。
  • 如果遍历对象时按照指定比较器递增排列,则由TreeSet类实现的Set集合存入的对象必须实现自定义比较器类。

TreeSet类通过实现java.util.SortedSet接口增加的方法如下:

  • comparator():获得对该集合采用的比较器,返回值为comparator类型,如果未采用任何比较器则返回null。
  • first():返回在集合中的排序位于第一的对象。
  • last():返回在集合中的排序位于最后的对象。
  • headSet(E toElement):截取在toElement(不包含)之前的所有对象,重新生成一个Set集合并返回。
  • subSet(E fromElement, E toElement):截取在fromElement(包含)之后,toElement(不包含)之前- 的所有对象,重新生成一个Set集合并返回。
  • tail(E fromElement):截取在fromElement(包含)之后的所有对象,重新生成一个Set集合并返回。
2.1 按照自然顺序递增排列

【例】使用TreeSet类。创建一个Person类,由TreeSet类实现的Set集合中的对象要求必须实现java.lang.Comparable接口,这里实现的排序方式为按编号升序排列。
代码如下:

import java.util.Set;
import java.util.TreeSet;
import java.util.Iterator;
import java.util.SortedSet;

class Person implements Comparable{
    private String name;
    private long id_card;
    public Person(String name, long id_card){
        this.name = name;
        this.id_card = id_card;
    }
    public String getName(){
        return this.name;
    }
    public long getId_card(){
        return this.id_card;
    }
    public void setName(String name){
        this.name = name;
    }
    public void setId_card(long id_card){
        this.id_card = id_card;
    }

    public int compareTo(Object obj){
        Person person = (Person)obj;
        int result = (this.id_card > person.id_card) ? 1 : (this.id_card == person.id_card ? 0 : -1);
        return result;
    }
}

public class testTreeSet {
    public static void main(String[] args){
        TreeSet<Person> treeSet = new TreeSet<Person>();
        Person person1 = new Person("马先生", 220181);
        Person person2 = new Person("李先生", 220186);
        Person person3 = new Person("王小姐", 220193);
        Person person4 = new Person("尹先生", 220196);
        Person person5 = new Person("王先生", 220175);
        treeSet.add(person1);
        treeSet.add(person2);
        treeSet.add(person3);
        treeSet.add(person4);
        treeSet.add(person5);

        System.out.println("初始化的集合:");
        Iterator<Person> it = treeSet.iterator();
        while(it.hasNext()){
            Person person = it.next();
            System.out.println("------ " + person.getName() + "  " + person.getId_card());
        }

        System.out.println("截取前面部分得到的集合:");
        //it = treeSet.headSet(person1).iterator();
        SortedSet<Person> treeSet1 = treeSet.headSet(person1);
        it = treeSet1.iterator();
        while(it.hasNext()){
            Person person = it.next();
            System.out.println("------ " + person.getName() + " " + person.getId_card());
        }

        System.out.println("截图中间部分得到的集合:");
        it = treeSet.subSet(person1, person3).iterator();
        while(it.hasNext()){
            Person person = it.next();
            System.out.println("------ " + person.getName() + " " + person.getId_card());
        }

        System.out.println("截取最后部分得到的集合:");
        it = treeSet.tailSet(person3).iterator();
        while(it.hasNext()){
            Person person = it.next();
            System.out.println("------ " + person.getName() + " " + person.getId_card());
        }           
    }
}

运行截图如下:
运行截图

2.2 按照指定比较器递增排列

【例】自定义比较器。在使用由TreeSet类实现的Set集合时,通过单独的比较器对集合中的对象进行排序,比较器类既可以作为一个单独的类,也可以作为对应类的内部类,这里以单独类为例。

代码如下:

import java.util.Comparator;
import java.util.Iterator;
import java.util.TreeSet;

class Person implements Comparable{
    private String name;
    private long id_card;
    public Person(String name, long id_card){
        this.name = name;
        this.id_card = id_card;
    }
    public String getName(){
        return this.name;
    }
    public long getId_card(){
        return this.id_card;
    }
    public void setName(String name){
        this.name = name;
    }
    public void setId_card(long id_card){
        this.id_card = id_card;
    }

    public int compareTo(Object obj){
        Person person = (Person)obj;
        int result = (this.id_card > person.id_card) ? 1 : (this.id_card == person.id_card ? 0 : -1);
        return result;
    }
}

//user_defined comparator
class PersonComparator implements Comparator{
    public static final int NAME = 1;
    public static final int ID_CARD = 2;
    private int orderByColumn = 1; //default sort by name 
    public static final boolean ASC = true;
    public static final boolean DESC = false;
    private boolean orderByMode = true; //default sort by ASC
    @Override
    public int compare(Object obj1, Object obj2) {
        // TODO Auto-generated method stub
        int result = 0;
        Person person1 = (Person)obj1;
        Person person2 = (Person)obj2;
        switch(orderByColumn){
        case 2:
            if(orderByMode)
                result = (int)(person1.getId_card() - person2.getId_card());
            else
                result = (int)(person2.getId_card() - person1.getId_card());
            break;
        default:
            String s1 = person1.getName();
            String s2 = person2.getName();
            if(orderByMode)
                result = s1.compareTo(s2);
            else
                result = s2.compareTo(s1);
        }
        return result;
    }
    public void orderByColumn(int orderByColumn){
        this.orderByColumn = orderByColumn;
    }
    public void orderByMode(boolean orderByMode){
        this.orderByMode = orderByMode;
    }

}

public class UserDefinedCompraratorTS {
    public static void main(String[] args){
        Person p1 = new Person("Mr ma", 220181);
        Person p2 = new Person("Mr li", 220186);
        Person p3 = new Person("Miss wang", 220193);
        TreeSet<Person> treeSet = new TreeSet<Person>();
        treeSet.add(p1);
        treeSet.add(p2);
        treeSet.add(p3);
        System.out.println("客户化排序前,默认按编号升序排序:");
        TreeSet<Person> treeSet2 = new TreeSet<Person>(treeSet);
        Iterator<Person> it = treeSet2.iterator();
        while(it.hasNext()){
            Person person = it.next();
            System.out.println("------" + person.getId_card() + " " + person.getName());
        }
        System.out.println("客户化排序后,按编号降序排序:");
        PersonComparator pc3 = new PersonComparator();
        pc3.orderByColumn(PersonComparator.ID_CARD);
        pc3.orderByMode(PersonComparator.DESC);
        TreeSet<Person> treeSet3 = new TreeSet<Person>(pc3);
        treeSet3.addAll(treeSet);
        it = treeSet3.iterator();
        while(it.hasNext()){
            Person person = it.next();
            System.out.println("------" + person.getId_card() + " " + person.getName());
        }
        System.out.println("客户化排序后,按姓名升序排序:");
        PersonComparator pc4 = new PersonComparator();
        pc4.orderByColumn(PersonComparator.NAME);
        TreeSet<Person> treeSet4 = new TreeSet<Person>(pc4);
        treeSet4.addAll(treeSet);
        it = treeSet4.iterator();
        while(it.hasNext()){
            Person person = it.next();
            System.out.println("------" + person.getId_card() + " " + person.getName());
        }
    }
}

运行截图如下:
运行截图

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值