Collection子接口:其二 Set 组接口

- Set接口是Collection的子接口,Set没有提供额外的方法

- Set集合中不允许包含重复的元素,如果重复添加,只保留最新添加的那一个

- Set判断两个元素是否相同不是 == 判断,而是取equals()方法

Set主要实现类:

HashSet、LinkedHashSet、TreeSet

- HashSet  Set主要接口实现类、线程不安全的、可存储Null值

- LinkedHashSet  继承了HashSet、遍历内部数据,可按照添加时的顺序遍历

- TreeSet  底层存储结构是红黑树【二叉树】,按照指定属性进行排序

Set底层的说明,红康老师讲的还是不解,决定留在数据结构篇再来细谈

https://www.bilibili.com/video/BV1Kb411W75N?p=537

底层算法的哈希码

https://www.cnblogs.com/mindzone/p/12736516.html

 1 public class CollectionTest {
2 public static void main(String[] args) {
3 Set set = new HashSet();
4
5 set.add("阿伟");
6 set.add("杰哥");
7 set.add("1376");
8 set.add("先辈");
9 set.add("Van");
10 set.add("佟大为");
11 set.add("1376");
12 set.add(new Student("小明",12));
13 set.add(new Student("小明",12));
14
15 Iterator iterator = set.iterator();
16
17 while(iterator.hasNext()){
18 Object next = iterator.next();
19 System.out.println(next);
20 }
21 // 阿伟 Van 1376 佟大为 杰哥 先辈
22 // 无序性不是遍历的结果没有顺序(不是随机性) 存储的数据不是按照索引顺序排列的,根据数据的Hash值添加
23 // 不可重复性 这里添加了同一字符串1376,从哈希码可以判断是一样,set集合只会保留其中一个
24
25 // 如果是对象就不一样了,这里依然会保留两个同属性对象,底层哈希码是不一样的
26 // 再重写equals & hashCode 之后只保留一个对象了, 调用add方法时,set会调用对象的equals方法判断,为true将不会添加
27 }
28 }
29
30
31 class Student{
32 private String name;
33 private Integer age;
34
35 public String getName() {
36 return name;
37 }
38
39 public void setName(String name) {
40 this.name = name;
41 }
42
43 public Student(String name, Integer age) {
44 this.name = name;
45 this.age = age;
46 }
47
48 public Integer getAge() {
49 return age;
50 }
51
52 public void setAge(Integer age) {
53 this.age = age;
54 }
55
56 @Override
57 public String toString() {
58 return "Student{" +
59 "name='" + name + '\'' +
60 ", age=" + age +
61 '}';
62 }
63
64 @Override
65 public boolean equals(Object o) {
66 if (this == o) return true;
67 if (!(o instanceof Student)) return false;
68 Student student = (Student) o;
69 return Objects.equals(getName(), student.getName()) &&
70 Objects.equals(getAge(), student.getAge());
71 }
72
73 @Override
74 public int hashCode() {
75 return Objects.hash(getName(), getAge());
76 }
77 }

LinkedHashSet,是HashSet的子类

添加数据的同时每个数据维护了两个引用,记录前一个数据和后一个数据

对于频繁的遍历操作,LinkedHashSet效率高于HashSet

public class CollectionTest {
public static void main(String[] args) {
Set set = new LinkedHashSet(); set.add("阿伟");
set.add("杰哥");
set.add("1376");
set.add("先辈");
set.add("Van");
set.add("佟大为");
set.add("1376"); Iterator iterator = set.iterator(); while(iterator.hasNext()){
Object next = iterator.next();
System.out.println(next);
}
}
}

TreeSet存储的数据只能是同一个类型的数据

自定义数据类型或者其他的基本类型封装类

TreeSet方式的判断是以Comparable接口实现的compareTo方法操作的【自然排序方式】

0 表示相同 TreeSet将会认为是重复,不再添加重复的元素

 1 public class CollectionTest {
2 public static void main(String[] args) {
3 Set set = new TreeSet();
4
5 set.add(new Person("Jimmy",17));
6 set.add(new Person("Mike",13));
7 set.add(new Person("Jim",15));
8 set.add(new Person("Jack",12));
9 set.add(new Person("Jerry",18));
10 set.add(new Person("Jack",56));
11
12 Iterator iterator = set.iterator();
13
14 while(iterator.hasNext()){
15 Object next = iterator.next();
16 System.out.println(next);
17 }
18 }
19 }
20
21
22 // 需要实现Comparable接口
23 class Person implements Comparable{
24 private String name;
25 private Integer age;
26
27 public Person(String name, Integer age) {
28 this.name = name;
29 this.age = age;
30 }
31
32 public String getName() {
33 return name;
34 }
35
36 public void setName(String name) {
37 this.name = name;
38 }
39
40 public Integer getAge() {
41 return age;
42 }
43
44 public void setAge(Integer age) {
45 this.age = age;
46 }
47
48 @Override
49 public String toString() {
50 return "Person{" +
51 "name='" + name + '\'' +
52 ", age=" + age +
53 '}';
54 }
55
56 // 重写此方法
57 @Override
58 public int compareTo(Object o) {
59 if (o instanceof Person){
60 Person p = (Person)o;
61 int compare = this.name.compareTo(p.name); // 掉用String的compareTo方法,不是本地的
62 if (compare != 0) return compare;
63 else return Integer.compare(this.age,p.age); // 如果相同,再compare第二属性
64 }else throw new RuntimeException("装入的类型不匹配!");
65 }
66 }

详细红黑树可以参考自视频里面的这篇链接,作者博客已经搬迁了啊

https://www.yycoding.xyz/post/2014/3/27/introduce-red-black-tree

除了上面的自然排序,也支持定制排序

 1 public class CollectionTest {
2 public static void main(String[] args) {
3 Comparator comparator = new Comparator() {
4 // 按照年龄从小到大排列,一样剔除
5 @Override
6 public int compare(Object o1, Object o2) {
7 if (o1 instanceof Person && o2 instanceof Person){
8 Person p1 = (Person)o1;
9 Person p2 = (Person)o2;
10 return Integer.compare(p1.getAge(),p2.getAge());
11 }else throw new RuntimeException("类型不匹配!");
12 }
13 };
14
15 // 如果定义了定制排序,创建Set集合初始化时,注入定制比较器,TreeSet就会默认使用此比较
16 Set set = new TreeSet(comparator);
17
18 set.add(new Person("Jimmy",17));
19 set.add(new Person("Mike",13));
20 set.add(new Person("Jim",15));
21 set.add(new Person("Jack",12));
22 set.add(new Person("Jerry",18));
23 set.add(new Person("Jack",56));
24
25 Iterator iterator = set.iterator();
26
27 while(iterator.hasNext()){
28 Object next = iterator.next();
29 System.out.println(next);
30 }
31 }
32 }
33
34
35 // 需要实现Comparable接口
36 class Person implements Comparable{
37 private String name;
38 private Integer age;
39
40 public Person(String name, Integer age) {
41 this.name = name;
42 this.age = age;
43 }
44
45 public String getName() {
46 return name;
47 }
48
49 public void setName(String name) {
50 this.name = name;
51 }
52
53 public Integer getAge() {
54 return age;
55 }
56
57 public void setAge(Integer age) {
58 this.age = age;
59 }
60
61 @Override
62 public String toString() {
63 return "Person{" +
64 "name='" + name + '\'' +
65 ", age=" + age +
66 '}';
67 }
68
69 // 重写此方法
70 @Override
71 public int compareTo(Object o) {
72 if (o instanceof Person){
73 Person p = (Person)o;
74 int compare = this.name.compareTo(p.name); // 掉用String的compareTo方法,不是本地的
75 if (compare != 0) return compare;
76 else return Integer.compare(this.age,p.age); // 如果相同,再compare第二属性
77 }else throw new RuntimeException("装入的类型不匹配!");
78 }
79 }

没有写定制排序才会按照equals方法排序

【Java】Collection子接口:其二 Set 组接口的更多相关文章

  1. Java基础-Collection子接口之Set接口

    Java基础-Collection子接口之Set接口 作者:尹正杰 版权声明:原创作品,谢绝转载!否则将追究法律责任. 学习Collection接口时,记得Collection中可以存放重复元素,也可 ...

  2. Java基础-Collection子接口之List接口

    Java基础-Collection子接口之List接口 作者:尹正杰 版权声明:原创作品,谢绝转载!否则将追究法律责任. 我们掌握了Collection接口的使用后,再来看看Collection接口中 ...

  3. Java学习关于集合框架的基础接口--Collection接口

     集合框架(Collection  Framework)是Java最强大的子系统之一,位于java.util 包中.集合框架是一个复杂的接口与和类层次,提供了管理对象组的最新技术.Java集合框架标准 ...

  4. java Collection接口

    Collection 1——————Set子接口:无序,不允许重复. 2——————List子接口:有序,允许重复. Set和List对比: 1.set:检索元素的效率比较低,删除和插入效率比较高,删 ...

  5. Collection子接口(List/Set/Queue/SortedSet)

    Collection基本的子接口: List:能够存放反复内容 Set:不能存放反复内容,全部反复的内容靠hashCode()和equals()两个方法区分 Queue:队列接口 SortedSet: ...

  6. Java面向对象之 接口: [修饰符] interface 接口名 {...};子接口:[修饰符] interface 接口名 extends 父接口,父接口2...{...}

    1.什么是接口? 类比抽象类,把功能或者特性类似的一类 抽象的更彻底,可以提炼出更加特殊的"抽象类"----接口 2.如何定义接口 语法:  [修饰符] interface 接口名 ...

  7. Effective Java 第三版——41.使用标记接口定义类型

    Tips <Effective Java, Third Edition>一书英文版已经出版,这本书的第二版想必很多人都读过,号称Java四大名著之一,不过第二版2009年出版,到现在已经将 ...

  8. 自顶向下理解Java集合框架(三)Map接口

    Map基本概念 数据结构中Map是一种重要的形式.Map接口定义的是查询表,或称查找表,其用于储存所谓的键/值对(key-value pair),其中key是映射表的索引. JDK结构中还存在实现Ma ...

  9. 数据结构-List接口-LinkedList类-Set接口-HashSet类-Collection总结

    一.数据结构:4种--<需补充> 1.堆栈结构:     特点:LIFO(后进先出);栈的入口/出口都在顶端位置;压栈就是存元素/弹栈就是取元素;     代表类:Stack;     其 ...

  10. Java基础知识笔记(七:接口、变量作用域和参数传递)

    一.接口 Java语言不允许一个子类拥有多个直接父类,即任何子类只能有一个直接父类.但允许一个类实现多个接口,即在定义类的接口名称列表中可以包含1个或多个接口名称,从而实现多重继承的特性.接口的定义格 ...

随机推荐

  1. Apisix网关-使用Grafana可视化Apisix的Prometheus数据

    Apisix安装部署 Apisix官网安装教程 Apisix Dashboard官网安装教程 本次教程使用RPM包安装方式 使用systemctl管理服务 Apisix配置要点 /usr/local/ ...

  2. ES6 ES6变量的声明

      // ES6语法         // 是对js影响最大的一个版本更新         // 在 ES6 语法中 退出了很多新的 语法结构         // 就相当于 js 语言, 换了一个新 ...

  3. Vue学习:17.组件通信案例-记事本

    通过上一节的学习,我们了解并掌握了组件通信的定义及一般使用.那么接下来,我们将之前练习过的案例使用组件化思想来实现一下吧. 实例:记事本(组件化) 实现功能 运用组件化思想,实现Vue学习:3.V标签 ...

  4. Mysql RC/RR隔离原理和区别 不可重复读和可重复读

    Mysql RC/RR隔离原理和区别 不可重复读和可重复读 mysql四种隔离级别:1.未提交读(READ UNCOMMITED)脏读2.已提交读 (READ COMMITED)简称(RC) 不可重复 ...

  5. oppo、一加 android14 chrome116内核 input @click不触发

    // 兼容Chrome内核116及以上版本中配置disabled的input组件无法触发并冒泡click事件 .uni-input-input:disabled { pointer-events: n ...

  6. [一句话说iOS]dispatch如何造成死锁

    dispatch_sync执行了两件事:把代码块放入指定线程的任务队列中.堵塞当前线程直到代码块执行结束,如果出现了堵塞的线程和代码块所在的线程为同一线程的话,这个时候代码无法在此线程执行继续下去,即 ...

  7. BST-Treap名次树数组&指针实现板子 Ver1.0

    这里只有板子没有原理QWQ 可实现 1.插入 x 数 2.删除 x 数(若有多个相同的数,只删除一个) 3.查询 x 数的排名(排名定义为比当前数小的数的个数 +1) 4.查询排名为 x 的数 5.求 ...

  8. 文件系统(八):Linux JFFS2文件系统工作原理、优势与局限

    liwen01 2024.06.23 前言 在嵌入式Linux设备中,经常使用jffs2文件系统来作为参数区的文件系统格式.至于为什么要使用jffs2来作为参数区的文件系统,我猜大部分人都没有做过多的 ...

  9. UART和RS232、RS485的关系是什么?

    串口通讯是电子工程师和嵌入式开发工程师面对的最基本问题,RS232则是其中最简单最常用的通讯方式.但是初学者往往搞不清有关的名词如UART和RS232或RS485之间是什么关系,因为它们经常被放到语句 ...

  10. Oracle常用统计

    测试, 这是测消息 1.按天 select to_char(t.STARTDATE+15/24, 'YYYY-MM-DD') as 天,sum(1) as 数量from HOLIDAY tgroup ...