用单链表实现集合

news2024/10/7 6:41:58

一、实验题目

(1)实验题目
用单链表实现集合
(2)问题描述
用有序单链表实现集合的判等、交、并和差等基本运算。

二、实验内容

(1)采用有序单链表存储集合;
(2)实现交、并、差等基本运算时,要求算法的空间复杂度为 O(1);
(3)充分利用单链表的有序性,要求算法有较好的时间性能;
(4)分析算法的时空性能,设计测试数据并上机实现。

三、数据结构设计

//节点结构
static class ListNode {
public int val;
public ListNode next;
public ListNode(int val) {
this.val = val;
}
}
//判断集合 A 和 B 是否相等
public boolean isEqual(ListNode curA , ListNode curB)
//求集合 A 和 B 的交集
public ListNode Interest(ListNode curA , ListNode curB)
//求集合 A 和 B 的并集
public ListNode union(ListNode curA , ListNode curB)
//差集
public ListNode subtraction(ListNode curA , ListNode curB)

四、算法设计

(1)判断集合 A 和 B 是否相等
public boolean isEqual(ListNode curA , ListNode curB)
同时遍历A链表和B链表
ListNode pa = curA
ListNode pb = curB
循环条件:pa != null && pb != null
如果pa.val!=pb.val,返回false,如果pa.val=pb.val,pa=pa.next,pb=pb.next,直到循环 结束。如果两个链表都为空,直接返回true,否则返回false.
时间复杂度:O(N)
空间复杂度:O(1)

(2)求集合 A 和 B 的交集
public ListNode Interest(ListNode curA , ListNode curB)
ListNode pa = curA
ListNode pb = curB
首先循环遍历B链表,每遍历一个节点,去遍历链表A,如果A链表的值小于 B节点的值,需要将该节点删除,删除就需要定义prev,让prev指向要删除节点的前驱节点,prev.next = pa.next,当pa.val=pb.val,说明链表A中包含pa节点,让prev = pa,pa=pa.next,pb=pb.next,如果pa.val> pb.val,pb=pb.next.
最终返回A链表的头节点即可。
时间复杂度:O(N^2)
空间复杂度:O(1)

(3)求集合 A 和 B 的并集
public ListNode union(ListNode curA , ListNode curB)
遍历B链表的每个节点,每遍历到一个节点去判断A链表中是否包含该节点如果A链表中该节点,pb=pb.next,同时再次循环A链表中的每个节点,如果A链表中不包含该节点,使用尾插法将该节点插入到A链表中,prev .next = pb; prev = prev.next , prev.next = null;注意,将该链表插入到A链表后,需要将尾节点的next域置null,为了能够找到B链表的下一个节点,需要引入ListNode pbNext = pb.next;,定义在B链表每次进入循环的时候,防止找不到B链表的后续节点。
时间复杂度:O(N^2)
空间复杂度:O(1)

(4)差集
public ListNode subtraction(ListNode curA , ListNode curB)
遍历B链表的每个节点,遍历到每个节点的同时,遍历A链表,如果A链表中包含该节点,需要将该节点删除,如果不包含该节点,继续遍历B链表中的下一个节点即可。
时间复杂度:O(N^2)
空间复杂度:O(1)

五、运行结果 在这里插入图片描述

在这里插入图片描述
在这里插入图片描述
在这里插入图片描述

七、程序源码


```java
public class MyLinkedList {
    //节点结构
    static class ListNode {
        public int val;
        public ListNode next;
        public ListNode(int val) {
            this.val = val;
        }
    }
    public ListNode createList(String str){
        LinkedList<ListNode> list = new LinkedList<>();
        for (int i = 0; i < str.length(); i++) {
            char ch = str.charAt(i);
            int n = Integer.valueOf(ch)-48;
            ListNode node = new ListNode(n);
            list.add(node);
        }
        for (int i = 0; i < list.size()-1; i++) {
            ListNode node  = list.get(i);
           ListNode node2 =list.get(i+1);
           node.next = node2;
        }
        ListNode last = list.get(list.size()-1);
        last.next = null;
        return list.get(0);
    }
    //判断集合 A 和 B 是否相等
    public boolean  isEqual(ListNode curA , ListNode curB){
        if(curA == null && curB == null){
            return true;
        }
        if(curA != null && curB == null || curA == null && curB !=null){
            return false;
        }
        //curA != null && curB != null
        ListNode pa = curA;
        ListNode pb =curB;
        while(pa != null && pb != null){
           if(pa.val != pb.val){
               return false;
           }
           pa =pa.next;
           pb = pb.next;
        }
        if(pa == null && pb == null){
            return true;
        }else{
            return false;
        }
    }
    //求集合 A 和 B 的交集
    /**
     *
     * @param curA: 表示链表A的头结点
     * @param curB: 表示链表B的头结点
     * @return
     */
    public ListNode Interest(ListNode curA , ListNode curB){
        if(curA == null && curB == null){
            return null;
        }
        if(curA != null && curB == null || curA == null && curB !=null){
            return null;
        }
        //curA != null && curB != null
        ListNode pa = curA;
        ListNode pb =curB;
        ListNode prev =null;
        while(pa != null && pb !=null){
            if(pa.val < pb.val){
                if(pa == curA){
                    curA = curA.next;
                    pa = pa.next;
                }else {
                    prev.next = pa.next;
                    pa = pa.next;
                }
            }else if(pa.val > pb.val){
                pb = pb.next;
            }else {
                prev = pa;
                pa = pa.next ;
                pb =pb.next;
            }
        }
//        prev.next = null;
        return curA ;
    }
    //求集合 A 和 B 的并集
    public ListNode union(ListNode curA , ListNode curB){
        ListNode pb = curB;
        int flg = 0 ;
        ListNode prev = null;
        while(pb != null){
            ListNode pbNext = pb.next;
            flg = 0;
            ListNode pa = curA ;
            prev = null;
            while(pa != null){
                if(pa.val == pb.val){
                    flg = 1;
                    break;
                }
                prev = pa;
                pa = pa.next;
            }
            if(flg == 0){
                prev .next = pb;
                prev = prev.next;
                prev.next = null;
            }
            pb =pbNext;

        }

        return curA;
    }
    //差集
    public ListNode subtraction(ListNode curA , ListNode curB) {
        ListNode pb =curB;
         while(pb != null) {
            ListNode pa =curA;
            ListNode prev = null;
            while(pa != null){
                if(pa.val == pb.val){
                    if(pa == curA){
                        curA = curA.next;
                    }else {
                        prev.next = pa.next;
                    }
                    break;
                }
                //不相等,改变前驱节点
                prev = pa;
                pa = pa.next;
            }
            pb =pb.next;
        }
       return curA;
    }
    public void print(ListNode cur){
        while(cur != null){
            System.out.print(cur.val + " ");
            cur =cur.next;
        }
        System.out.println();
    }

}
public class Test {
    public static void main(String[] args) {
        MyLinkedList myLinkedList = new MyLinkedList();
        System.out.println("请输入链表A的节点:");
        Scanner scanner = new Scanner(System.in);
        String strA = scanner.nextLine();
        System.out.println("请输入链表B的节点:");
        String strB = scanner.nextLine();
        MyLinkedList.ListNode curA  =  myLinkedList.createList(strA);
        MyLinkedList.ListNode curB  =  myLinkedList.createList(strB);
        System.out.print("链表A和链表B是否相等: ");
        System.out.println(myLinkedList.isEqual(curA, curB));
       MyLinkedList.ListNode node =  myLinkedList.Interest(curA, curB);
       System.out.print("链表A和链表B的交集是: ");
        myLinkedList.print(node);
        MyLinkedList.ListNode node2 = myLinkedList.union(curA,curB);
        System.out.print("链表A和链表B的并集是: ");
       myLinkedList.print(node2);
        MyLinkedList.ListNode node3 = myLinkedList.subtraction(curA,curB);
        System.out.print("链表A和链表B的差集是: ");
        myLinkedList.print(node3);
    }
}

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

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

相关文章

vue实现pdf下载——html2canvas

html2canvas 官方文档https://html2canvas.hertzen.com/getting-started html2canvas 的原理是通过遍历DOM树,将每一个HTML元素转化为Canvas对象,并叠加到一起形成一张完整的图片或者PDF文件。 1. 安装插件 npm install html2canvas jspdf --save 2.使用&#xff08;页面已经…

PVE安装虚拟主机

本文记录PVE安装其他虚拟主机的步骤&#xff0c;以安装win-server为例。裸机安装PVE则不是本文主题。 准备文件 获取Windows系统镜像 win server镜像可以从官网获取普通Windows镜像可从MSDN获取此外&#xff0c;安装Windows系统还需要从PVE下载特殊驱动 获取Windows必要驱动 …

网络安全形势与WAF技术分享

我一个朋友的网站&#xff0c;5月份时候被攻击了&#xff0c;然后他找我帮忙看看&#xff0c;我看他的网站、网上查资料&#xff0c;不看不知道&#xff0c;一看吓一跳&#xff0c;最近几年这网络安全形势真是不容乐观&#xff0c;在网上查了一下资料&#xff0c;1、中国信息通…

【网络安全的神秘世界】web应用程序安全与风险

&#x1f31d;博客主页&#xff1a;泥菩萨 &#x1f496;专栏&#xff1a;Linux探索之旅 | 网络安全的神秘世界 | 专接本 第一章&#xff1a;web应用程序安全与风险 web攻击基础知识 1、什么是web应用攻击 web攻击的本质&#xff0c;就是通过http协议篡改应用程序&#xff0…

手撸 串口交互命令行 及 AT应用层协议解析框架

在嵌入式系统开发中&#xff0c;命令行接口&#xff08;CLI&#xff09;和AT命令解析是常见的需求。CLI提供了方便的调试接口&#xff0c;而AT命令则常用于模块间的通信控制。本文将介绍如何手动实现一个串口交互的命令行及AT应用层协议解析框架&#xff0c;适用于FreeRTOS系统…

机器学习多场景实战

机器学习已不再局限于理论探讨&#xff0c;而是广泛渗透到我们生活的方方面面&#xff0c;成为解决复杂问题、优化决策过程的强有力工具。从智能推荐系统个性化推送你可能喜爱的电影和商品&#xff0c;到金融风控领域精准识别欺诈交易&#xff1b;每一个应用场景都是机器学习技…

Spring Boot项目中,如何在yml配置文件中读取maven pom.xml文件中的properties标签下的属性值

一、前言 在最近的项目开发过程中&#xff0c;有一个需求&#xff0c;需要在Spring Boot项目的yml配置文件中读取到mave的 pom.xml文件中的properties标签下的属性值&#xff0c;这个要怎么实现呢&#xff1f; 二、技术实践 pom.xml文件中增加测试属性 <properties><…

【数据结构】筛选法建堆

&#x1f49e;&#x1f49e; 前言 hello hello~ &#xff0c;这里是大耳朵土土垚~&#x1f496;&#x1f496; &#xff0c;欢迎大家点赞&#x1f973;&#x1f973;关注&#x1f4a5;&#x1f4a5;收藏&#x1f339;&#x1f339;&#x1f339; &#x1f4a5;个人主页&#x…

Golang | Leetcode Golang题解之第134题加油站

题目&#xff1a; 题解&#xff1a; func canCompleteCircuit(gas []int, cost []int) int {for i, n : 0, len(gas); i < n; {sumOfGas, sumOfCost, cnt : 0, 0, 0for cnt < n {j : (i cnt) % nsumOfGas gas[j]sumOfCost cost[j]if sumOfCost > sumOfGas {break}…

Android 14.0 Settings主页面去掉自定义您的设备等菜单相关功能

1.前言 在14.0的系统rom产品定制化开发中,在系统Settings主页面的主菜单中,在测试某些功能的时候,比如开启护眼模式和改变系统密度会在主菜单第一项的网络菜单头部增加 自定义您的设备和设置护眼模式时间安排 等等相关的设置模块 这对于菜单布局显示相当不美观,所以根据系…

TSR,FSR,DLSS超级分辨率的原理分析

先了解一些时域抗锯齿的方法&#xff1a; TAA&#xff1a; 抖动 TAA 的主要原理是跨帧计算多个子像素样本&#xff0c;然后将它们组合成一个最终像素。最简单的方案是在像素内生成随机样本&#xff0c;但有更好的方法来生成固定序列的样本。选择一个好的序列以避免聚集非常重…

MacOS 安装C语言版TensorFlow

文章目录 安装C语言版TensorFlow解压归档环境变量c_api.hC语言示例 安装C语言版TensorFlow 官方文档&#xff1a;https://tensorflow.google.cn/install/lang_c?hlzh-cnTensorFlow 提供了一个 C API&#xff0c;该 API 可用于为其他语言构建绑定。该 API 在 c_api.h 中定义&a…

我有点想用JDK17了

大家好呀&#xff0c;我是summo&#xff0c;JDK版本升级的非常快&#xff0c;现在已经到JDK20了。JDK版本虽多&#xff0c;但应用最广泛的还得是JDK8&#xff0c;正所谓“他发任他发&#xff0c;我用Java8”。 其实我也不太想升级JDK版本&#xff0c;感觉投入高&#xff0c;收…

【TB作品】 51单片机8x8点阵显示滚动汉字仿真

功能 题目5基于51单片机LED8x8点阵显示 流水灯 直接滚动显示HELLO 直接滚动显示老师好 代码 void main( void ) {/** 移位后&#xff0c;右边的是第一个595&#xff0c;接收0X02&#xff0c;显示出0X02* 移位后&#xff0c;左边的是第2个595&#xff0c;接收0Xfe&#xff0c…

C++结合OpenCV进行图像处理与分类

⭐️我叫忆_恒心&#xff0c;一名喜欢书写博客的在读研究生&#x1f468;‍&#x1f393;。 如果觉得本文能帮到您&#xff0c;麻烦点个赞&#x1f44d;呗&#xff01; 近期会不断在专栏里进行更新讲解博客~~~ 有什么问题的小伙伴 欢迎留言提问欧&#xff0c;喜欢的小伙伴给个三…

人工智能任务5-高级算法工程师需要学习哪些课程与掌握哪些能力

大家好&#xff0c;我是微学AI&#xff0c;今天给大家介绍一下人工智能的任务5-高级算法工程师需要学习哪些课程&#xff0c;需要掌握哪些能力。高级算法工程师需要掌握的算法模型有&#xff1a;人脸检测模型MTCNN&#xff0c;人脸识别方法Siamese network、center loss、softm…

在VSCode中安装python

引言 Python 是一种广泛使用的高级编程语言&#xff0c;因其易学、易用、强大而受到欢迎。它由 Guido van Rossum 于 1991 年首次发布&#xff0c;并以简洁的语法和丰富的库生态系统而著称。 以下是 Python 的一些关键特点和优势&#xff1a; 关键特点 易于学习和使用&#x…

AWS的EC2之间ping不通,服务之间不通,怎么办

AWS启动的两个EC2实例&#xff0c;互相访问不了 修改安全组规则&#xff0c;添加ICMP 流量的入站规则 参考&#xff1a;AWS的EC2之间ping不通,服务之间不通,怎么办_aws ec2同一个区域的服务器-CSDN博客

选择排序-Java版本

选择排序 算法的思想&#xff1a;java模拟 算法的思想&#xff1a; 每遍历一次就找一个最小的数 *外层 一共遍历 length-1次 总遍历次数符合等差数列 时间复杂度为O(n^2)内部查找 并 返回 数值 和 下标 java模拟 public static void selectSort(int[] arr) {for(int i 0;i<…

MyBatis拦截器使用方法

前言 MyBatis拦截器可以做的工作&#xff1a;SQL修改&#xff0c;分页操作&#xff0c;数据过滤&#xff0c;SQL执行时间性能监控等。 1. 基础介绍 1.1. 核心对象 从MyBatis代码实现的角度来看&#xff0c;MyBatis的主要的核心部件有以下几个&#xff1a; Configuration&am…