黑马程序员 java基础之set集合



------Java培训、Android培训、iOS培训、.Net培训、期待与您交流! -------

  Set

一、概述

        Set:元素是无序(存入和取出的顺序不一定一致),元素不可以重复。     

           |--HashSet:底层数据结构是哈希表。线程不同步。 保证元素唯一性的原理:判断元素的hashCode值是否相同。如果相同,还会继续判断元素的equals方法,是否为true

           |--TreeSet:可以对Set集合中的元素进行排序。默认按照字母的自然排序。底层数据结构是二叉树。保证元素唯一性的依据:compareTo方法return 0

        Set集合的功能和Collection是一致的。

 

二、HasSet

        HashSet:线程不安全,存取速度快。

       可以通过元素的两个方法,hashCodeequals来完成保证元素唯一性。如果元素的HashCode值相同,才会判断equals是否为true。如果元素的hashCode值不同,不会调用equals

注意:HashSet对于判断元素是否存在,以及删除等操作,依赖的方法是元素的hashCodeequals方法。


/*
往hashSet集合中存入自定对象
姓名和年龄相同为同一个人,重复元素。去除重复元素
思路:1、对人描述,将人的一些属性等封装进对象
	  2、定义一个HashSet容器,存储人对象
	  3、取出

*/
import java.util.*;

//人描述
class Person
{
	private String name;
	private int age;

	Person(String name,int age)
	{
		this.name=name;
		this.age=age;
	}

	public String getName()
	{
		return name;
	}

	public int getAge()
	{
		return age;
	}

	public boolean equals(Object obj)
	{
		if(!(obj instanceof Person))
			return false;
		Person p=(Person)obj;
		return this.name.equals(p.name)&&this.age==p.age;
	}

	public int hashCode()
	{
		return this.name.hashCode()+this.age;
	}
}
class  HashSetTest
{
	public static void main(String[] args) 
	{
		HashSet h=new HashSet();
		h.add(new Person("shenm",10));
		h.add(new Person("shenm2",6));
		h.add(new Person("shenm1",30));
		h.add(new Person("shenm0",10));
		h.add(new Person("shenm0",10));
		
		getOut(h);

	}

	//取出元素
	public static void getOut(HashSet h)
	{
		for (Iterator it=h.iterator(); it.hasNext(); )
		{
			Person p=(Person)it.next();
			sop(p.getName()+"..."+p.getAge());
		}
	}

	//打印
	public static void sop(Object obj)
	{
		System.out.println(obj);
	}
}

三、TreeSet

1、特点

        a、底层的数据结构为二叉树结构(红黑树结构)

        b)可对Set集合中的元素进行排序,是因为:TreeSet类实现了Comparable接口,该接口强制让增加到集合中的对象进行了比较,需要复写compareTo方法,才能让对象按指定需求(如人的年龄大小比较等)进行排序,并加入集合。

        java中的很多类都具备比较性,其实就是实现了Comparable接口。

注意:排序时,当主要条件相同时,按次要条件排序。

  c、保证数据的唯一性的依据:通过compareTo方法的返回值,是正整数、负整数或零,则两个对象较大、较小或相同。相等时则不会存入。

2Tree排序的两种方式


1)第一种排序方式:自然排序

        让元素自身具备比较性。元素需要实现Comparable接口,覆盖compareTo方法。这种方式也被称为元素的自然顺序,或者叫做默认顺序。

示例:

import java.util.*;
//学生类
class Student implements Comparable
{
	private String name;
	private int age;
	Student(String name,int age)
	{
		this.name=name;
		this.age=age;
	}
	public String getName()
	{
		return name;
	}

	public int getAge()
	{
		return age;
	}
	//复写hashCode以便HashSet集合调用
	public int hashCode()
	{
		return name.hashCode()+age;
	}
	//复写equals以便HashSet集合和集合中一些比较方法调用
	public boolean equals(Object obj)
	{
		if(!(obj instanceof Student))
			throw new RuntimeException();
		Student s = (Student)obj;
		return this.name.equals(s.name)&&this.age==s.age;
	}
	//复写compareTo以便TreeSet集合调用
	public int compareTo(Object obj)
	{
		Student s=(Student)obj;
		if(this.age==s.age)
			return this.name.compareTo(s.name);
		return this.age-s.age;
		//return new Integer(this.age).compareTo(new Integer(s.age)); 
	}
}

class  TreeSetTest
{
	public static void main(String[] args) 
	{
		TreeSet t=new TreeSet();
		t.add(new Student("wo1",12));
		t.add(new Student("wosj",2));
		t.add(new Student("wo1sdj",12));
		t.add(new Student("wo6sd",12));
		t.add(new Student("wo",22));

		
		for (Iterator it=t.iterator(); it.hasNext(); )
		{
			Student s=it.next();
			System.out.println(s.getName()+"....."+s.getAge());
		}
	}
}
2 )第二种方式:比较器

        当元素自身不具备比较性时,或者具备的比较性不是所需要的。这时就需要让集合自身具备比较性。

        在集合初始化时,就有了比较方式。定义一个比较器,将比较器对象作为参数传递给TreeSet集合的构造函数。

        比较器构造方式:定义一个类,实现Comparator接口,覆盖compare方法。

        当两种排序都存在时,以比较器为主。

示例:

/*
需求:
往TreeSet集合中存储自定义对象学生。
想按照学生的年龄进行排序。

*/

import java.util.*;
//学生类
class Student implements Comparable
{
	private String name;
	private int age;
	Student(String name,int age)
	{
		this.name=name;
		this.age=age;
	}
	public String getName()
	{
		return name;
	}

	public int getAge()
	{
		return age;
	}
	//复写hashCode以便HashSet集合调用
	public int hashCode()
	{
		return name.hashCode()+age;
	}
	//复写equals以便HashSet集合和集合中一些比较方法调用
	public boolean equals(Object obj)
	{
		if(!(obj instanceof Student))
			throw new RuntimeException();
		Student s = (Student)obj;
		return this.name.equals(s.name)&&this.age==s.age;
	}
	//复写compareTo以便TreeSet集合调用
	public int compareTo(Object obj)
	{
		Student s=(Student)obj;
		if(this.age==s.age)
			return this.name.compareTo(s.name);
		return this.age-s.age;
		//return new Integer(this.age).compareTo(new Integer(s.age)); 
	}

}

class  TreeSetTest
{
	public static void main(String[] args) 
	{
		TreeSet t=new TreeSet(new LenCompare());
		t.add(new Student("wo1",12));
		t.add(new Student("wosj",2));
		t.add(new Student("wo1sdj",12));
		t.add(new Student("wo6sd",12));
		t.add(new Student("wo",22));

		
		for (Iterator it=t.iterator(); it.hasNext(); )
		{
			Student s=it.next();
			System.out.println(s.getName()+"....."+s.getAge());
		}
	}

}
//定义一个比较器,以姓名长度为主要比较
class LenCompare implements Comparator
{
	public int compare(Student s1,Student s2)
	{
		int num=new Integer(s1.getName().length()).compareTo(new Integer(s2.getName().length()));
		if (num==0)
		{
			return new Integer(s1.getAge()).compareTo(s2.getAge());
		}
		return num;
	}
}


你可能感兴趣的:(黑马程序员 java基础之set集合)