5-1 LC148 排序链表 Java力扣刷题笔记

LC148 排序链表

我的刷题笔记
排序链表

0.刷题前需知

这题…虽然算在我们的快速排序专题中
但是这个题不要用快排!因为时间复杂度比题目要求要高!
但是!!
在这里插入图片描述
在这里插入图片描述
在这里插入图片描述
特么面试要考。
啥都得练呗

1.读题

给你链表的头结点 head 请将其按照升序排列 并返回 排序后的链表
在这里插入图片描述

2.解题思路

参考题解 排序链表(快排方式)
面试官:你写个链表快排吧(不准交换节点的值哦)
之前还写过一篇快排的小文——三板斧实现快速排序! 可以康康 python实现的 挺清楚的~
先复习下快排思想——

【1】只有一个元素 直接返回这个元素
【2】选定一个pivot基准
【3】小于pivot的分在一边 大于pivot的分在一遍 (这个过程也叫partition分区)

这里注意了!数组的分区是很好做的!左右两个指针不断交换即可!
但是我们这个是链表。。。。。
链表只能单向遍历 所以我们要换一个“partition分区”的方法
在这里插入图片描述
浏览了下大佬面字节时候的过程
来看看大佬是怎么想这道题的~

3.代码逻辑

借鉴下大佬的解题思路

【1】选取头节点作为基准值pivot(之前不说是pivot随便儿取不影响时间复杂度嘛~)
【2】遍历链表 比基准值(也就是头节点)小的节点头插在它前面
【2‘】比基准值大的节点尾插在它后面
【3】假设lhead维护的是小于基准值的头插指针
【3’】utail维护的是大于等于基准值的尾插指针
【4】一次对[head , end)快排结束后得到——
【4’】[lhead, head) 这是小于基准值的那一部分
【4‘’】[lhead.next,end) 这是大于基准值的哪部分
【5】分别递归这两部分 最后做一个拼接~

4.Java代码

class Solution {
    public ListNode sortList(ListNode head) {
        return quicksort(head, null);
    }

    public static ListNode quicksort(ListNode head, ListNode end){
        if(head == end || head.next == end) return head;//【1】设置退出条件

        ListNode lhead = head, utail = head, p = head.next;//[3]维护小于基准值的头插指针lhead 大于基准值的尾插指针utail 
        while (p != end){
            ListNode next = p.next;
            if (p.val < head.val){//进行头插
                p.next = lhead;
                lhead = p;
            }
            else {//进行尾插
                utail.next = p;
                utail = p;
            }
            p = next;
        }
        utail.next = end;
        ListNode node = quicksort(lhead, head);
        head.next = quicksort(head.next, end);
        return node;
        
    }
}

终于是成功了一次!
总之 这个快排单链表的方法还是能不用就不用!太容易失败了!
在这里插入图片描述

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值