一、LinkedHashSet特点
二、LinkedHashSet原理(引入双链表 -----有序)
三、TreeSet原理
1.对自定义对象进行排序
方法1(实现Compareable接口 重写比较规则)
import java.util.Objects;
public class Student implements Comparable<Student>{
private String name;
public int age;
private double height;
@Override//比较规则的重写
public int compareTo(Student o) {
return this.age-o.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 && Double.compare ( student.height, height ) == 0 && Objects.equals ( name, student.name );
}
@Override
public int hashCode() {//只要两个对象内容一样就返回一样的哈希值
return Objects.hash ( name, age, height );//根据 姓名 年龄 身高 计算哈希值
}
public Student() {
}
public Student(String name, int age, double height) {
this.name = name;
this.age = age;
this.height = height;
}
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;
}
public double getHeight() {
return height;
}
public void setHeight(double height) {
this.height = height;
}
@Override
public String toString() {
return "Student{" +
"name='" + name + '\'' +
", age=" + age +
", height=" + height +
'}';
}
}
方法2 使用比较器对象进行排序
import java.util.Comparator;
import java.util.Set;
import java.util.TreeSet;
public class SetTest4 {
public static void main(String[] args) {
Student s1 =new Student ("猪猪侠",25,169.5);
Student s2 =new Student ("菲菲公主",22,166.5);
Student s3 =new Student ("猪猪",21,169.5);
Set<Student> set=new TreeSet<> ( new Comparator<Student> () {//比较器对象
@Override
public int compare(Student o1, Student o2) {
return Double.compare ( o1.getHeight (),o2.getHeight () );
}
} );
set.add ( s1 );
set.add ( s2 );
set.add ( s3 );
System.out.println ( set );//[Student{name='猪猪', age=21, height=169.5}, Student{name='菲菲公主', age=22, height=166.5}, Student{name='猪猪侠', age=25, height=169.5}]
}
}
四、各种实现类集合所适合的业务场景
五、集合的并发修改异常问题
一边遍历一边删除 时索引也会改变,所以会造成漏删
使用增强for循环没有办法补救
import java.util.ArrayList;
import java.util.Iterator;
import java.util.List;
public class collectionExcepttionTest {
public static void main(String[] args) {
List<String> list =new ArrayList<> ();
list.add ( "王麻子" );
list.add ( "张三" );
list.add ( "李四" );
list.add ( "李阳" );
list.add ( "李陌陌" );
list.add ( "张强" );
list.add ( "王强" );
Iterator<String> it = list.iterator ();
while (it.hasNext ()){
String name = it.next ();
if (name.contains ( "李" )){
list.remove ( name );
}
}
System.out.println (list);
}
}
解决方法(为for循环 加入i--||使用迭代器自带的remove方法 )
import java.util.ArrayList;
import java.util.Iterator;
import java.util.List;
public class collectionExcepttionTest {
public static void main(String[] args) {
List<String> list =new ArrayList<> ();
list.add ( "王麻子" );
list.add ( "张三" );
list.add ( "李四" );
list.add ( "李阳" );
list.add ( "李陌陌" );
list.add ( "张强" );
list.add ( "王强" );
Iterator<String> it = list.iterator ();
// while (it.hasNext ()){
// String name = it.next ();
// if (name.contains ( "李" )){
// list.remove ( name );
// }
// }
// System.out.println (list);
// for (int i = 0; i < list.size (); i++) {
// String name=list.get ( i );
// if (name.contains ( "李" )){
// list.remove ( name );
//
// }
// }
// System.out.println ( list );//[王麻子, 张三, 李阳, 张强, 王强] 有漏删
System.out.println ("-----------------------------------------------------------------------");
// for (int i = 0; i < list.size (); i++) {
// String name=list.get ( i );
// if (name.contains ( "李" )){
// list.remove ( name );
// i--; //每删除一个索引减一,指针回退1 避免漏删
// }
// }
while (it.hasNext ()){
String name = it.next ();
if (name.contains ( "李" )){
// list.remove ( name );
it.remove ();//删除迭代器当前遍历得到的数据,每删除一个数据后 也相当于在底层做了i--
}
}
System.out.println (list);
}
}