无序链表排序_双向链表排序算法

无序链表排序_双向链表排序算法需求给定一个无序的链表,输出有序的链表。分析链表排序比较特殊,由于不连续的性质,所以在进行排序的时候要引入外排思想,因此归并排序或者多路归并就成为了排序的选择。归并排序分为拆分、合并两个阶段:1.拆分需要拆分出链表中间节点,并赋值NULL阶段,形成两个独立的链表,直到拆分成单个节点为止。2.合并由于此时没个链表都为单节点,所以实质上是个有序链表合并问题。代码下面

大家好,又见面了,我是你们的朋友全栈君。如果您正在找激活码,请点击查看最新教程,关注关注公众号 “全栈程序员社区” 获取激活教程,可能之前旧版本教程已经失效.最新Idea2022.1教程亲测有效,一键激活。

Jetbrains全系列IDE稳定放心使用

需求

给定一个无序的链表,输出有序的链表。

分析

链表排序比较特殊,由于不连续的性质,所以在进行排序的时候要引入外排思想,因此归并排序或者多路归并就成为了排序的选择。
归并排序分为拆分、合并两个阶段:
1. 拆分
需要找出链表中间节点,并根据中间节点拆分成两个独立的链表,递归直到拆分成单个节点为止。
2. 合并
由于此时每个链表都为单节点,所以对于拆分的两个子链表实质上是有序链表合并问题。

代码

下面是示例代码

    private class Node {
        int value;
        Node next;
    }

    private Node getRandomList(int length)
    {
        Node node = new Node();
        int randomNum = (int) ((Math.random() * 100) % 100);
        node.value = randomNum;
        Node head = node;
        for(int i = 0; i < length; i++)
        {
            randomNum = (int) ((Math.random() * 100) % 100);
            Node temp = new Node();
            temp.value = randomNum;
            node.next = temp;
            node = temp;
        }

        return head;
    }

    private Node getMiddleNode(Node head)
    {
        Node index1 = head;
        Node index2 = head;
        while(index2.next != null && index2.next.next != null)
        {
            index1 = index1.next;
            index2 = index2.next.next;
        }

        return index1;
    }

    private Node mergeSort(Node head)
    {
        if(head.next == null)
            return head;

        Node middelNode = getMiddleNode(head);
        Node head1 = head;
        Node head2 = middelNode.next;
        middelNode.next = null;

        head1 = mergeSort(head1);
        head2 = mergeSort(head2);

        Node currenthead = mergeSequentialList(head1, head2);

        return currenthead;
    }

    private Node mergeSequentialList(Node head1, Node head2)
    {

        if(head1 == null)
            return head2;
        if(head2 == null)
            return head1;
        Node currentNode = null;
        if(head1.value < head2.value)
        {
            head1.next = mergeSequentialList(head1.next, head2);
            currentNode = head1;
        }
        else
        {
            head2.next = mergeSequentialList(head1, head2.next);
            currentNode = head2;
        }

        return currentNode;
    }

    private int outputListValue(Node list, StringBuffer bf) {
        // TODO Auto-generated method stub

        int i = 0;
        while(list.next != null)
        {
            bf.append(list.value + "-");
            i++;
            list = list.next;
        }
        return i;
    }


    public void main()
    {
        Node list = getRandomList(50);
        list = mergeSort(list);
        StringBuffer bf = new StringBuffer();
        int count = outputListValue(list, bf);
        String result = bf.toString();  
    }

复杂度

对于中间节点的查找,可以使用两指针不同步调方式,查找的时间复杂度为O(n)。
对于两个有序子链表合并,递归深度为最短链表深度,时间复杂度为O(n)。
由于归并排序会调用logn次,所以最终的时间复杂度为(2n)logn = O(nlogn)。

总结

无序链表排序考察的知识点比较多,首先要深刻理解归并排序的思想与应用场景,其次算法中也运用到了链表中间节点查找、两个有序链表归并等单算法,并且也要考虑单算法其中的细节。整体算法难度比较难。

版权声明:本文内容由互联网用户自发贡献,该文观点仅代表作者本人。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如发现本站有涉嫌侵权/违法违规的内容, 请联系我们举报,一经查实,本站将立刻删除。

发布者:全栈程序员-站长,转载请注明出处:https://javaforall.net/183150.html原文链接:https://javaforall.net

(0)
上一篇 2022年10月11日 下午3:00
下一篇 2022年10月11日 下午3:00


相关推荐

  • AI智能体(AI Agent): 概念、技术、趋势及其在制造业中的应用

    AI智能体(AI Agent): 概念、技术、趋势及其在制造业中的应用

    2026年3月15日
    2
  • VMware16的安装及VMware配置Linux虚拟机(详解版)

    VMware16的安装及VMware配置Linux虚拟机(详解版)前言为了Linux系统初学者的学习,以及不必要再花费成本与时间去安装Linux系统,使用VMware下配置Linux虚拟机进行学习也是个不错的选择。次文详解了VMware16软件的安装步骤,以及Linux虚拟机的CentOS7简易安装的步骤,操作简单,完全足够Linux系统初学者的学习。VMware软件下载地址:https://www.vmware.com/cn/products/workstation-pro/workstation-pro-evaluation.htmlCentOS7下载映像

    2022年7月16日
    48
  • 深入浅出TCP三次握手 (多图详解)[通俗易懂]

    深入浅出TCP三次握手 (多图详解)[通俗易懂]文章目录前言1、TCP是什么?2、TCP首部格式3、TCP的连接建立4、三次握手图文详解5、三次握手文字总结5、是否可以使用“两报文握手”建立连接?6、两次握手文字总结前言TCP三次握手和四次挥手是面试题的热门考点,它们分别对应TCP的连接和释放过程,今天我们先来认识一下TCP三次握手过程,以及是否可以使用“两报文握手”建立连接?。1、TCP是什么?TCP是面向连接的协议,它基于运输连接来传送TCP报文段,TCP运输连接的建立和释放,是每一次面向连接的通信中必不可少的过程。TCP运输连接有以下

    2022年10月4日
    7
  • navicat premium 15 激活码 mac(JetBrains全家桶)「建议收藏」

    (navicat premium 15 激活码 mac)2021最新分享一个能用的的激活码出来,希望能帮到需要激活的朋友。目前这个是能用的,但是用的人多了之后也会失效,会不定时更新的,大家持续关注此网站~IntelliJ2021最新激活注册码,破解教程可免费永久激活,亲测有效,下面是详细链接哦~https://javaforall.net/100143.html…

    2022年3月21日
    153
  • 【Verilog-19.3】define和undef的用法

    【Verilog-19.3】define和undef的用法19 3 defineand undef 提供了文本宏替换功能 可以使用有意义的名称来表示常用的文本片段 例如 在整个描述中重复使用一个常数的情况下 文本宏是有用的 如果常数的值需要改变 因为它只需要更改源描述中的一个位置 文本宏工具不受编译器指令 resetall 的影响 19 3 1 define 指令 define 为文本替换创建了一个宏 这个指令可以在模块定义的内部和外部使用 一个文本宏定义以后 通过使用 字符 后面跟着宏的名字 它可以在源代码描述中使用 编译器应该用宏的文本替换字符串 t

    2026年3月18日
    2
  • web前端node.js常用命令

    web前端node.js常用命令1、npm install moduleNames:安装Node模块安装完毕后会产生一个node_modules目录,其目录下就是安装的各个node模块。node的安装分为全局模式

    2022年7月1日
    21

发表回复

您的邮箱地址不会被公开。 必填项已用 * 标注

关注全栈程序员社区公众号