TreeSet 是一个可以对元素进行排序的容器。底层实际是用 TreeMap 实现的,内部维持了一个简化版的 TreeMap,通过 key 来存储 Set 的元素。 TreeSet 内部需要对存储的元素进行排序,因此,我们需要给定排序规则。
排序规则实现方式:
- 通过元素自身实现比较规则。
- 通过比较器指定比较规则。
在元素自身实现比较规则时,需要实现 Comparable 接口中的 compareTo 方法,该方法中用来定义比较规则。TreeSet 通过调用该方法来完成对元素的排序处理。
package TreeSet;
import java.util.Set;
import java.util.TreeSet;
/*
* tree是顺序存储元素的
*
* */
public class TreeSetTest {
public static void main(String[] args) {
Set set = new TreeSet<>();
set.add("A");
set.add("B");
set.add("D");
set.add("E");
set.add("C");
for (String str: set) {
System.out.println(str);
}
/*在此处我们无序的加入了字母表中的元素,而输出结果会顺序输出,这是因为我们在存储过程中是会对
*元素调用compareTo进行排序的
*/
System.out.println("----------------------");
Set personSet = new TreeSet<>();
Person person = new Person("AAA",18);
Person person1 = new Person("AAA",21);
Person person2 = new Person("BBB",18);
Person person3 = new Person("BBB",13);
personSet.add(person);
personSet.add(person1);
personSet.add(person2);
personSet.add(person3);
for (Person p: personSet){
System.out.println(p);
}
/*在此处我们依然会率先按照年龄对对象的先后顺序进行调整,而后对对象的姓名进行排序,
*我们并没有让系统直接调用compareTo方法,而是对它进行了重写(见实体类重写)
*/
}
}
运行结果:
所以我们虽然加进去
我们先构造一个实体类:它包括姓名和id两个基本属性:
因为我们要构造实体对象,所以我们需要构造方法;
因为我们需要获取对象的值,所以我们需要get/set方法;
因为我们要输出的是对象的值而非存储位置的hashcode,所以我们需要重写toString方法;
因为我们要比较的是对象的具体值而非它的hashcode值,所以我们也要对java中的equals方法进行重写;
***因为Java中提供的compareTo函数是基于基本数据类型和String类型的比较,所以在对象比较的过程中我们也需要重写compraeTo方法; ***
package TreeSet;
import java.util.Objects;
public class Person implements Comparable {
private String name;
private int age;
public Person(String name, int age) {
this.name = name;
this.age = age;
}
//重写comparable方法就不会只是单纯比较字符了
@Override
public int compareTo(Person o) {
if (this.age > o.getAge()){
return 1;
}
if (this.age == o.age){
return this.name.compareTo(o.getName());
}
return -1;
}
//重写equals方法比较的就不止是hashcode值了,而是开始比较内容
@Override
public boolean equals(Object o) {
if (this == o) return true;
if (o == null || getClass() != o.getClass()) return false;
Person person = (Person) o;
return age == person.age &&
Objects.equals(name, person.name);
}
@Override
public int hashCode() {
return Objects.hash(name, age);
}
public String getName() {
return name;
}
public void setName(String name) {
this.name = name;
}
public int getAge() {
return age;
}
public void setAge(int age) {
this.age = age;
}
//重写toString,输出时候就不会只出现地址值了
@Override
public String toString() {
return "Person{" +
"name='" + name + '\'' +
", age=" + age +
'}';
}
}
那么接下来我们自己创建一个比较器:
我们创建一个Student的实体类,属性依旧只有name和id
对它进行get/set方法获取,进行构造方法使用。对toString进行重写。也对equals方法进行重写。
package TreeSet;
import java.util.Objects;
public class Student{
private String name;
private int age;
public Student(String name, int age) {
this.name = name;
this.age = age;
}
public String getName() {
return name;
}
public void setName(String name) {
this.name = name;
}
public int getAge() {
return age;
}
public void setAge(int age) {
this.age = age;
}
@Override
public String toString() {
return "Student{" +
"name='" + name + '\'' +
", age=" + age +
'}';
}
@Override
public boolean equals(Object o) {
if (this == o) return true;
if (o == null || getClass() != o.getClass()) return false;
Student student = (Student) o;
return age == student.age &&
Objects.equals(name, student.name);
}
@Override
public int hashCode() {
return Objects.hash(name, age);
}
}
接下来我们再写一个构造器类:
这里我们一定是util包里面的comparator接口;
我们实现这个接口,
package TreeSet;
import java.util.Comparator;
public class StuComparator implements Comparator {
@Override
public int compare(Student o1, Student o2) {
if(o1.getAge()>o2.getAge()){
return 1;
}
if (o1.getAge() == o2.getAge()){
return o1.getName().compareTo(o2.getName());
//调用String的compareTo方法对字符串进行排序并进行返回(正数:大。负数:小。相等:0)
}
return -1;
}
}
主方法:
package TreeSet;
import java.util.Set;
import java.util.TreeSet;
public class TestComparator {
public static void main(String[] args) {
Set studentSet = new TreeSet<>(new StuComparator());
//在这里我们是可以调用我们所实现排序的比较器的规则进行排序
Student student = new Student("cde",18);
Student student1 = new Student("efg",13);
Student student2 = new Student("abc",18);
studentSet.add(student);
studentSet.add(student1);
studentSet.add(student2);
for (Student stu:studentSet ) {
System.out.println(stu);
}
}
}
欢迎分享,转载请注明来源:内存溢出
评论列表(0条)