一、Set接口与List接口的区别
1.List:不唯一,有序,遍历方式(普通for循环,增强for循环、迭代器)
2.Set:唯一(不能存入相同元素),无序(相对于List来说无序,但不等于随机)
遍历方式(增强for循环、迭代器),因为Set里没有与索引相关的方法,所以不能使用普通for循环遍历
二、HashSet实现类
1.HashSet的特点:唯一、无序
2.HashSet的使用
import java.util.HashSet;
public class Demo14 {
public static void main(String[] args) {
//创建一个HashSet集合,泛型为Integer
HashSet<Integer> hs1 = new HashSet<>();
hs1.add(10);
hs1.add(11);
hs1.add(12);
hs1.add(13);
//HashSet是唯一的,不能放入重复数据
hs1.add(10);
//可以利用add()方法返回的布尔值来查看是否添加,可以看到第二个14返回值是false,没有添加
System.out.println(hs1.add(14)); //true
System.out.println(hs1.add(14)); //false
System.out.println(hs1); //[10, 11, 12, 13]
//泛型为String,与上面同理
HashSet<String> hs2 = new HashSet<>();
hs2.add("aa");
hs2.add("bb");
hs2.add("cc");
hs2.add("dd");
hs2.add("bb");
System.out.println(hs2);
}
}
在HashSet中可以存放系统定义好的引用数据类型,也可以放自己定义的数据类型,但是必须重写equals()和hashCode()方法
import java.util.HashSet;
public class Demo14 {
public static void main(String[] args) {
//泛型为自己定义的引用类型,与上面同理
HashSet<Student1> hs3 = new HashSet<>();
hs3.add(new Student1(10,"小明"));
hs3.add(new Student1(18,"小红"));
hs3.add(new Student1(25,"张三"));
hs3.add(new Student1(47,"李四"));
hs3.add(new Student1(18,"小红"));
System.out.println(hs3.size());//5,重复的数据也被添加进去了
System.out.println(hs3);
//[Student1{age=18, name='小红'}, Student1{age=47, name='李四'},
// Student1{age=10, name='小明'}, Student1{age=25, name='张三'},
// Student1{age=18, name='小红'}]
}
}
class Student1{
private int age;
private String name;
public Student1(int age, String name) {
this.age = age;
this.name = name;
}
public int getAge() {
return age;
}
public void setAge(int age) {
this.age = age;
}
public String getName() {
return name;
}
public void setName(String name) {
this.name = name;
}
@Override
public String toString() {
return "Student1{" +
"age=" + age +
", name='" + name + '\'' +
'}';
//对于需要放入Set中的数据的类型,一定要重写equals()和hashCode()两个方法。
//否则会导致该对象失去Set的唯一,无序的特点,任意引用数据类型如Integer、String中也都会重写这两个方法
@Override
public boolean equals(Object o) {
if (this == o) return true;
if (o == null || getClass() != o.getClass()) return false;
Student1 student1 = (Student1) o;
return age == student1.age && Objects.equals(name, student1.name);
}
@Override
public int hashCode() {
return Objects.hash(age, name);
}
}
3.HashSet底层原理:数组+链表=哈希表
三、LinkedHashSet实现类
1.LinkedHashSet特点:唯一,有序(在HashSet上多了一个链表来方便元素排序)
//在HashSet的基础上,唯一且有序
LinkedHashSet<String> lkhs = new LinkedHashSet<>();
lkhs.add("aa");
lkhs.add("bb");
lkhs.add("cc");
lkhs.add("dd");
lkhs.add("bb");
System.out.println(lkhs); //[aa, bb, cc, dd]