TreeSet概述
reeSet 是 SortedSet 接口的实现类,TreeSet 可以确保集合元素处于排序状态。
方法:
Comparator comparator()
Object first()
Object last()
Object lower(Object e)
Object higher(Object e)
SortedSet subSet(fromElement, toElement)
SortedSet headSet(toElement)
SortedSet tailSet(fromElement)
TreeSet 两种排序方法:自然排序和定制排序。默认情况下,TreeSet 采用自然排序。
自然排序
概述:
一、自然排序:TreeSet 会调用集合元素的 compareTo(Object obj) 方法来比较元素之间的大小关系,然后将集合元素按升序排列
二、如果试图把一个对象添加到 TreeSet 时,则该对象的类必须实现 Comparable 接口。
三、实现 Comparable 的类必须实现 compareTo(Object obj) 方法,两个对象即通过 compareTo(Object obj) 方法的返回值来比较大小。
四、Comparable 的典型实现:
BigDecimal、BigInteger 以及所有的数值型对应的包装类:按它们对应的数值大小进行比较
Character:按字符的 unicode值来进行比较
Boolean:true 对应的包装类实例大于 false 对应的包装类实例
String:按字符串中字符的 unicode 值进行比较
Date、Time:后边的时间、日期比前面的时间、日期大
步骤:
自然排序:
①要求添加进TreeSet中的元素所在的类implements Comparable接口
②重写compareTo(Object obj),在此方法内指明按照元素的哪个属性进行排序
③向TreeSet中添加元素即可。若不实现此接口,会报运行时异常
@Test
//TreeSet:
/*
* 1、元素必须是同一个类
* 2、可以按照添加进集合中的元素的顺序遍历。像String,包装类等默认按照从小到大的顺序遍历
* 3、当自定义类没有实现Comparable的接口时,要实现compareTo方法
*
* 5、向Tree中添加元素时,首先要按照compareTO进行比较,一旦返回0,虽然
* 两对象此属性相同,但程序会认为这两个对象相同
*/
public void test3() {//自然排序
Set set=new TreeSet();
/*set.add(123);
set.add(456);
set.add(113);
set.add(458);*/
set.add(new Person(11,"samuro11"));
set.add(new Person(12,"samuro1"));
set.add(new Person(13,"samuro3"));
set.add(new Person(14,"samuro4"));
set.add(new Person(14,"samuro5"));
for(Object str:set) {
System.out.println(str);
}
}
插入对象代码,跟接下来的定制排序共用(定制排序不需要实现Comparable接口)
public class Person implements Comparable{
private Integer age;
protected String name;
int id=1001;
public int getAge() {
return age;
}
public String getName() {
return name;
}
public void setName(String name) {
this.name = name;
}
public void setAge(int age) {
this.age = age;
}
public Person() {// 默认定义的,一旦显示定义构造器,显示的构造器不再提供,构造器重载
age = 18;
}
public Person(int age,String name) {
this.age = age;
this.name=name;
}
@Override
public String toString() {
return "Person [age=" + age + ", name=" + name + ", id=" + id + "]";
}
@Override
public int hashCode() {
final int prime = 31;
int result = 1;
result = prime * result + age;
result = prime * result + id;
result = prime * result + ((name == null) ? 0 : name.hashCode());
return result;
}
@Override
public boolean equals(Object obj) {
if (this == obj)
return true;
if (obj == null)
return false;
if (getClass() != obj.getClass())
return false;
Person other = (Person) obj;
if (age != other.age)
return false;
if (id != other.id)
return false;
if (name == null) {
if (other.name != null)
return false;
} else if (!name.equals(other.name))
return false;
return true;
}
@Override//实现核心
public int compareTo(Object o) {
// TODO Auto-generated method stub
if (o instanceof Person) {
Person person=(Person)o;
/*return this.name.compareTo(person.name);*/
/*return this.age.compareTo(person.age);*///加个负号,从大到小
int i=this.age.compareTo(person.age);
if (i==0) {
return this.name.compareTo(person.name);
}else {
return i;
}
}
return 0;
}
}
定制排序
概述:
一、向 TreeSet 中添加元素时,只有第一个元素无须比较compareTo()方法,后面添加的所有元素都会调用compareTo()方法进行比较。
二、因为只有相同类的两个实例才会比较大小,所以向 TreeSet 中添加的应该是同一个类的对象
三、对于 TreeSet 集合而言,它判断两个对象是否相等的唯一标准是:两个对象通过 compareTo(Object obj) 方法比较返回值
四、当需要把一个对象放入 TreeSet 中,重写该对象对应的 equals() 方法时,应保证该方法与 compareTo(Object obj) 方法有一致的结果:如果两个对象通过 equals() 方法比较返回 true,则通过 compareTo(Object obj) 方法比较应返回 0
步骤:
定制排序:
①创建一个实现Comparator接口的实现类的对象。在实现类中重写Comparator的compare(Object o1,Object o2)方法
②在此compare()方法中指明按照元素所在类的哪个属性进行排序
③将此实现Comparator接口的实现类的对象作为形参传递给TreeSet的构造器中
④向TreeSet中添加元素即可。若不实现此接口,会报运行时异常
@Test
public void test4() {
/*
* 1、创建一个Comparator(区别于CompareTo)接口的类对象
*/
Comparator comparator=new Comparator() {
/*
* 向TreeSet中添加Customer类的对象,再次compare()方法中
* 指明是按照cunstomer的哪个属性来排序的
*
*/
@Override
public int compare(Object o1, Object o2) {
if(o1 instanceof Customer&&o2 instanceof Customer) {
Customer customer1=(Customer)o1;
Customer customer2=(Customer)o2;
int i= customer1.getId().compareTo(customer2.getId());
if(i==0) {
return customer1.getName().compareTo(customer2.getName());
}else {
return i;
}
}
return 0;
}
//2、将此对象作为形参传递给TreeSet构造器中
};
TreeSet set=new TreeSet(comparator);
//3、向TreeSet中添加COmparator接口中的compare方法中涉及的类对象
set.add(new Customer("AA",1001));
set.add(new Customer("BB",1006));
set.add(new Customer("CC",1003));
set.add(new Customer("dd",1004));
set.add(new Customer("EE",1005));
for(Object o:set) {
System.out.println(o);
}
}