javase Set集合

news2024/11/26 10:45:33

Collection子接口2:Set

5.1 Set接口概述

  • Set接口是Collection的子接口,Set接口相较于Collection接口没有提供额外的方法

  • Set 集合不允许包含相同的元素,如果试把两个相同的元素加入同一个 Set 集合中,则添加操作失败。

  • Set集合支持的遍历方式和Collection集合一样:foreach和Iterator。

  • Set的常用实现类有:HashSet、TreeSet、LinkedHashSet。

5.2 Set主要实现类:HashSet

5.2.1 HashSet概述
  • HashSet 是 Set 接口的主要实现类,大多数时候使用 Set 集合时都使用这个实现类。

  • HashSet 按 Hash 算法来存储集合中的元素,因此具有很好的存储、查找、删除性能。

  • HashSet 具有以下特点

    • 不能保证元素的排列顺序

    • HashSet 不是线程安全的

    • 集合元素可以是 null

  • HashSet 集合判断两个元素相等的标准:两个对象通过 hashCode() 方法得到的哈希值相等,并且两个对象的 equals()方法返回值为true。

  • 对于存放在Set容器中的对象,对应的类一定要重写hashCode()和equals(Object obj)方法,以实现对象相等规则。即:“相等的对象必须具有相等的散列码”。

  • HashSet集合中元素的无序性,不等同于随机性。这里的无序性与元素的添加位置有关。具体来说:我们在添加每一个元素到数组中时,具体的存储位置是由元素的hashCode()调用后返回的hash值决定的。导致在数组中每个元素不是依次紧密存放的,表现出一定的无序性。

5.2.2 HashSet中添加元素的过程:
  • 第1步:当向 HashSet 集合中存入一个元素时,HashSet 会调用该对象的 hashCode() 方法得到该对象的 hashCode值,然后根据 hashCode值,通过某个散列函数决定该对象在 HashSet 底层数组中的存储位置。

  • 第2步:如果要在数组中存储的位置上没有元素,则直接添加成功。

  • 第3步:如果要在数组中存储的位置上有元素,则继续比较:

    • 如果两个元素的hashCode值不相等,则添加成功;

    • 如果两个元素的hashCode()值相等,则会继续调用equals()方法:

      • 如果equals()方法结果为false,则添加成功。

      • 如果equals()方法结果为true,则添加失败。

    第2步添加成功,元素会保存在底层数组中。

    第3步两种添加成功的操作,由于该底层数组的位置已经有元素了,则会通过链表的方式继续链接,存储。

5.2.3 重写 hashCode() 方法的基本原则
  • 在程序运行时,同一个对象多次调用 hashCode() 方法应该返回相同的值。

  • 当两个对象的 equals() 方法比较返回 true 时,这两个对象的 hashCode() 方法的返回值也应相等。

  • 对象中用作 equals() 方法比较的 Field,都应该用来计算 hashCode 值。

注意:如果两个元素的 equals() 方法返回 true,但它们的 hashCode() 返回值不相等,hashSet 将会把它们存储在不同的位置,但依然可以添加成功。

 

5.2.4 重写equals()方法的基本原则
  • 重写equals方法的时候一般都需要同时复写hashCode方法。通常参与计算hashCode的对象的属性也应该参与到equals()中进行计算。

  • 推荐:开发中直接调用Eclipse/IDEA里的快捷键自动重写equals()和hashCode()方法即可。

    • 为什么用Eclipse/IDEA复写hashCode方法,有31这个数字?

 

首先,选择系数的时候要选择尽量大的系数。因为如果计算出来的hash地址越大,所谓的“冲突”就越少,查找起来效率也会提高。(减少冲突)

其次,31只占用5bits,相乘造成数据溢出的概率较小。

再次,31可以 由i*31== (i<<5)-1来表示,现在很多虚拟机里面都有做相关优化。(提高算法效率)

最后,31是一个素数,素数作用就是如果我用一个数字来乘以这个素数,那么最终出来的结果只能被素数本身和被乘数还有1来整除!(减少冲突)

5.2.5 练习

练习1:在List内去除重复数字值,要求尽量简单

package lecodePac;

import org.junit.Test;
import setStudy.Person;

import java.util.ArrayList;
import java.util.HashSet;
import java.util.List;

/**
 * ClassName: Eexoen
 * Package: lecodePac
 * Description:
 *
 * @Author 吴伟贤
 * @Create 2024/3/19 20:40
 * @Version 1.0
 */
public class Eexoen {
    public static List copyDivList(List list){
        HashSet set = new HashSet();
        for (Object obj : list) {
            set.add(obj);
        }
        ArrayList list1 = new ArrayList();
        for (Object obj: set ){
            list1.add(obj);
        }
        return list1;
    }

    public static void main(String[] args) {

        ArrayList list = new ArrayList();
        list.add(23);
        list.add(23);
        list.add(22);
        list.add(22);
        list.add(21);
        list.add(21);

//        List newList = copyDivList(list);
//        System.out.println(newList);
        List list1 = copyList(list);
        System.out.println(list1);

    }
 public static List copyList(List list){
//方式1;
        //     HashSet set = new HashSet();
//
//     for (Object obj : list) {
//         set.add(obj);
//     }
//     ArrayList al = new ArrayList();
//     for (Object obj : set) {
//          al.add(obj);
//     }
//     return al;
 //方式2:
     HashSet set = new HashSet(list);
     ArrayList list1 = new ArrayList(set);
     return list1;
 }


}

 

练习2:获取随机数

编写一个程序,获取10个1至20的随机数,要求随机数不能重复。并把最终的随机数输出到控制台。

  @Test
    public void test1() {
        HashSet set = new HashSet();
        while (set.size() < 10) {
            int random = (int) (Math.random() * (20 - 1 + 1) + 1);
            set.add(random);
        }
        Iterator iterator = set.iterator();
        while (iterator.hasNext()) {
            System.out.println(iterator.next());
        }
    }

面试题

package setStudy;

import java.nio.file.attribute.UserDefinedFileAttributeView;
import java.util.Objects;

/**
 * ClassName: Person
 * Package: setStudy
 * Description:
 *
 * @Author 吴伟贤
 * @Create 2024/3/19 14:06
 * @Version 1.0
 */
public class Person implements Comparable{
     String name;
     int age;

    public Person() {
    }

    public Person(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;
    }

    @Override
    public String toString() {
        return "Person{" +
                "name='" + name + '\'' +
                ", age=" + age +
                '}';
    }

    public void setAge(int age) {
        this.age = age;
    }

    @Override
    public boolean equals(Object o) {
        System.out.println("Person equals.....");
        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);
    }

    /**
     * 比较年龄从小到达排列,如果年龄相同,则继续比较姓名,从小到大
     * @param o
     * @return
     */
    @Override
    public int compareTo(Object o) {
        if(this == o){
            return 0;
        }
        if(o instanceof Person){
            Person p1 = (Person) o;
            int value = this.age - p1.age;
            if(value != 0){
                return value;
            }
            return this.name.compareTo(p1.name);
        }
        throw new RuntimeException("类型不匹配");
    }
}
@Test
    public void test1() {
        HashSet set = new HashSet();
        Person p1 = new Person("AA",1001);
        Person p2 = new Person("BB",1002);

        set.add(p1);
        set.add(p2);
        System.out.println(set);

        p1.name = "CC";
        set.remove(p1);
        System.out.println(set);

        set.add(new Person("CC",1001));
        System.out.println(set);

        set.add(new Person("AA",1001));
        System.out.println(set);
    }

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.coloradmin.cn/o/1530949.html

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈,一经查实,立即删除!

相关文章

红黑树简单介绍

1. 概念介绍 红黑树是一种自平衡二叉查找树&#xff0c;由于自平衡的特性&#xff0c;保证了最坏情况下在O&#xff08;logn&#xff09;时间复杂度内完成查找、增加、删除等操作&#xff0c;性能表现稳定。 在JDK中&#xff0c;TreeMap、TreeSet以及JDK1.8的HashMap底层都采用…

数据之王国:解析Facebook的大数据应用

引言 作为全球最大的社交媒体平台之一&#xff0c;Facebook拥有庞大的用户群体和海量的数据资源。这些数据不仅包括用户的个人信息和社交行为&#xff0c;还涵盖了广告点击、浏览记录等多方面内容。Facebook通过巧妙地利用这些数据&#xff0c;构建了强大的大数据应用系统&…

面向航天器大数据安全传输的发布/订阅系统设计

源自&#xff1a;系统工程与电子技术 作者&#xff1a;覃润楠 彭晓东 谢文明 惠建江 冯渭春 姜加红 “人工智能技术与咨询” 发布 摘 要 针对航天器试验任务过程监控的在轨故障诊断状态检测、健康状态评估与航天器寿命预测等多个环节中, 海量试验数据在传输、共享、处…

若依 无法导入表名过长的表格

原因 在mapper文件中&#xff0c;有很多转换的语句&#xff0c;使用的是nvarchar类型&#xff0c;nvarchar类型的长度很长&#xff0c;但是默认长度是30位。超过30位就会被截断 解决方案 找到mapper文件中所有对表名转换的地方&#xff0c;把长度扩大到100

电脑所有文档底色变绿?记好这4个方法就足够!

“这是怎么回事呢&#xff1f;怎么我的电脑里面所有文档底色都变绿了呢&#xff1f;我应该怎么操作才可以解决这个问题呀&#xff1f;” 在使用电脑的过程中&#xff0c;有时我们可能会遇到电脑所有文档底色变绿的情况。这种情况不仅影响了文档的阅读体验&#xff0c;还可能对视…

Visual Studio - 添加快捷键图标

Visual Studio - 添加快捷键图标 1. Text Editor Toolbar Options -> Add or Remove Buttons -> Customize2. Toolbars3. Commands -> Debug4. Add Command...References 1. Text Editor Toolbar Options -> Add or Remove Buttons -> Customize 2. Toolbars B…

【CSS】html滚动条相关

1.滚动条样式 ::-webkit-scrollbar {width: 10px;height: 10px;z-index: 101; } ::-webkit-scrollbar-thumb {border-radius: 5px;background: #cecece; } ::-webkit-scrollbar-track {// background: #f5f5f5be;background: rgba(33, 85, 163, 0); } ::-webkit-scrollbar-but…

热插拔技术详解(下)

4、热插拔导致的浪涌问题及其防治 &#xff08;1&#xff09;浪涌的概念 浪涌&#xff08;Electrical Surge&#xff09;顾名思义就是瞬间出现超出稳定值的峰值&#xff0c;它包括浪涌电压和浪涌电流。 浪涌电压是指超出正常工作电压的瞬间过电压&#xff1b;浪涌电流是指电源…

基于springboot+vue的疫情信息管理系统

博主主页&#xff1a;猫头鹰源码 博主简介&#xff1a;Java领域优质创作者、CSDN博客专家、阿里云专家博主、公司架构师、全网粉丝5万、专注Java技术领域和毕业设计项目实战&#xff0c;欢迎高校老师\讲师\同行交流合作 ​主要内容&#xff1a;毕业设计(Javaweb项目|小程序|Pyt…

AI助手 - 月之暗面 Kimi.ai

前言 这是 AI工具专栏 下的第四篇&#xff0c;这一篇所介绍的AI&#xff0c;也许是截至今天&#xff08;204-03-19&#xff09;国内可访问的实用性最强的一款。 今年年初&#xff0c;一直看到有人推荐 Kimi&#xff0c;不过面对雨后春笋般的各类品质的AI&#xff0c;说实话也有…

IP地址的分配:数字世界的地址规划者

在互联网的世界里&#xff0c;IP地址扮演着类似于房屋地址的角色&#xff0c;是用于标识和定位互联网上每个连接到网络的设备的唯一标识符。然而&#xff0c;这些IP地址并非随意分配&#xff0c;而是经过精心规划和管理的。本文将探讨IP地址的分配方式&#xff0c;揭示数字世界…

媒体邀约专访的意义?怎么做

传媒如春雨&#xff0c;润物细无声&#xff0c;大家好&#xff0c;我是51媒体网胡老师。 媒体邀约专访是指企业、组织或个人主动邀请媒体进行专题访谈的一种公关活动。这种活动对于提升品牌形象、传播信息、增强公众认知度和信任度等方面都有重要作用。以下是媒体邀约专访的一…

zabbix监控FortiGate防火墙 FortiGate配置SNMP

SNMP&#xff08;Simple Network Management Protocol&#xff09;是一种常用的监控方式。在Zabbix中&#xff0c;可以通过配置SNMP来监控网络设备和服务器。具体步骤如下&#xff1a; 1.FortiGate防火墙开启SNMP 登录防火墙&#xff0c;配置SNMP&#xff1a; 团体名称&#…

【探索Linux】—— 强大的命令行工具 P.28(网络编程套接字 —— 简单的UDP网络程序模拟实现)

阅读导航 引言一、UDP协议二、UDP网络程序模拟实现1. 预备代码⭕makefile文件⭕打印日志文件⭕打开指定的终端设备文件&#xff0c;并将其作为标准错误输出的目标文件描述符 2. UDP 服务器端实现&#xff08;UdpServer.hpp&#xff09;3. UDP 客户端实现&#xff08;main函数&a…

使用Redis做缓存的小案例

如果不了解Redis&#xff0c;可以查看本人博客&#xff1a;Redis入门 Redis基于内存&#xff0c;因此查询速度快&#xff0c;常常可以用来作为缓存使用&#xff0c;缓存就是我们在内存中开辟一段区域来存储我们查询比较频繁的数据&#xff0c;这样&#xff0c;我们在下一次查询…

服装行业实现数字化转型,只需上线这个系统!

近年来&#xff0c;内卷、降本增效等词频频冲上热搜&#xff0c;随着经济的周期性下行&#xff0c;服装企业的竞争愈发激烈&#xff0c;小单快返时代的到来&#xff0c;加速了服装行业的重新洗牌。在这样的大环境下&#xff0c;服装企业数字化转型几乎成了取得确定性增长的唯一…

QT网络编程之获取本机网络信息

一.概述 查询一个主机的MAC地址或者IP地址是网络应用中常用到的功能&#xff0c;Qt提供了QHostInfo和QNetworkInterface 类可以用于此类信息的查询 1.QHostInfo 类&#xff08;显示和查找本地的信息&#xff09; 2.QNetworkInterface 类&#xff08;获得应用程序上所在主机的…

Sublime Text3 C/C++一键调试运行代码

minGW的系统环境配置&#xff1a; 使用的C/C编译器是minGW&#xff0c;点此进入官网链接&#xff0c;下载后需要在线安装&#xff0c;安装后需要将安装目录下的bin目录所在路径加入path环境变量。本菜鸡的电脑里安装了CodeBlocks&#xff0c;在CodeBlocks的安装目录下有MinGW&…

婴儿洗衣机十大排名名牌:十款超高价值婴儿洗衣机综合整理

我们都知道宝宝的皮肤是超级娇嫩的&#xff0c;宝宝的衣物也一样&#xff0c;宝宝的衣物大部分都是纯棉的。如果将宝宝的衣物和大人衣服一起扔进大型洗衣机混洗&#xff0c;更可能出现细菌交叉感染&#xff0c;对小宝宝来说百害而无一利&#xff0c;会让小宝宝肌肤过敏、红肿、…

json字符串的数据提取

json的数据提取 学习目标 掌握 json相关的方法(load loads dump dumps)了解 jsonpath的使用(提取 json中的数据) 2 复习什么是json JSON(JavaScript Object Notation) 是一种轻量级的数据交换格式&#xff0c;它使得人们很容易的进行阅读和编写。同时也方便了机器进行解析和…