python每日一题 分隔链表

给你一个链表的头节点 head 和一个特定值 x ,请你对链表进行分隔,使得所有 小于 x 的节点都出现在 大于或等于 x 的节点之前。

你应当 保留 两个分区中每个节点的初始相对位置

我开始的想法想复杂了 想在原有的链表上进行操作 我开始写了一半的代码进行测验 就是将左边大于等于特定值的移动到右边去 于是就有了下列的代码

代码1

class ListNode(object):
     def __init__(self, val=0, next=None):
        self.val = val
        self.next = next
class Solution(object):
    def partition(self, head, x):
        dummy=ListNode(0)
        dummy.next=head
        pre=dummy
        current=head
        first_x=None
        while current!=None:
            if current.val==x:
                first_x=current
                break
            current=current.next
            #这样的话pre就是在first_x的前面
        if not first_x:
            return dummy.next
        #如果找到了,就算是等于x也要往后移
        left=head#初始化
        while left!=first_x:
            if left.val 
  

但是我忽略了一些事情 首先这个特定值并不一定在链表中存在 第二 这种方法修改了相对位置 比如这个最后测试的结果是1 -> 3 -> 5 -> 4 -> 2 -> 5 -> 2   5和4的位置不对 那么就需要移动first_x指针 但是这个指针是定数值的 所以这就需要再加上一个指针  我说这么多的意思就是告诉大家我我i什么又加上了一个first_x1指针 因为first_x指针你没法动他 它要决定你这个指针对应的数值是不是需要移动 但是你又必须要保持相对位置 所以你下一次插入绝对不可以在first_x后面 于是就有了下面的代码

代码2

class ListNode(object):
     def __init__(self, val=0, next=None):
        self.val = val
        self.next = next
class Solution(object):
    def partition(self, head, x):
        dummy=ListNode(0)
        dummy.next=head
        pre=dummy
        current=head
        first_x=None
        while current!=None:
            if current.val==x:
                first_x=current
                break
            current=current.next
            #这样的话pre就是在first_x的前面
        if not first_x:
            return dummy.next
        #如果找到了,就算是等于x也要往后移
        left=head#初始化
        first_x1=first_x
        while left!=first_x:
            if left.valleft.next=first_x1.next
                first_x1.next=left
                first_x1=left
                left=pre.next
        return dummy.next
    @staticmethod
    def list_to_linkedlist(lst):
        if not lst:
            return None
        head = ListNode(lst[0])
        current = head
        for val in lst[1:]:
            current.next = ListNode(val)
            current = current.next
        return head
    @staticmethod
    def print_linkedlist(head):
        current = head
        while current:
            print(current.val, end=" -> " if current.next else "")
            current = current.next
        print()  # 换行
solution=Solution()
result=solution.list_to_linkedlist([1,4,5,3,2,5,2])
result1=solution.partition(result,3)
result2=solution.print_linkedlist(result1)

好的现在左边的处理完了 我们来处理右边的 就是要让右边的小于特定数值的移动到左边 那么这个时候你是需要一个指针去记录first_x前面的 但是我的代码存在很多小问题 也是改了很多很多遍才完成下面的代码 虽然情况都是可以达到的 但是和题意不符 我真的是要噶过去了 红色部分的改进是针对于[2,1] 2这样的情况进行改进的 反正就是一直在加指针进行记录 一直在试情况

代码3

class ListNode(object):
     def __init__(self, val=0, next=None):
        self.val = val
        self.next = next
class Solution(object):
    def partition(self, head, x):
        if head==None or head.next==None:
            return head
        dummy=ListNode(0)
        dummy.next=head
        pre=dummy
        current=head
        first_x=None
        while current!=None:
            if current.val==x:
                first_x=current
                break
            current=current.next
            #这样的话pre就是在first_x的前面
        if not first_x:
            return dummy.next
        #如果找到了,就算是等于x也要往后移
        left=head#初始化
        first_x1=first_x
        while  left and left!=first_x:
            if left.val       temp = left.next
                # 将left节点插入到first_x1之后
                left.next = first_x1.next
                first_x1.next = left
                # 更新pre的next指针
                pre.next = temp
                first_x1=left
                left=pre.next
        pre1=dummy#用来找到前面排好序之后的first_x的前一个指针
        while pre1.next!=first_x and pre1.next:
              pre1=pre1.next
        pre=first_x1#用于断开指针的时候使用
        right=first_x1.next#从这个开始往后找 前面的都是之前插好的
        while right!=None:
            if right.val>=x:
                pre=right#记录right之前的指针
                right=right.next
            else:
                pre.next=right.next
                right.next=pre1.next
                pre1.next=right
                pre1=pre1.next
                right=pre.next
        return dummy.next
    @staticmethod
    def list_to_linkedlist(lst):
        if not lst:
            return None
        head = ListNode(lst[0])
        current = head
        for val in lst[1:]:
            current.next = ListNode(val)
            current = current.next
        return head
    @staticmethod
    def linkedlist_to_list(head):
        result = []
        current = head
        while current:
            result.append(current.val)
            current = current.next
        return result
solution=Solution()
result=solution.list_to_linkedlist([1,4,3,2,5,2])
result1=solution.partition(result,3)
result2=solution.linkedlist_to_list(result1)
print(result2)
#首先列表转链表 操作完之后链表转列表

但是我这个代码报错 报错的显示是输入这个 [1,4,3,2,5,2] 我的输出是[1, 2, 2, 3, 4, 5] 但是标准输出是[1,2,2,4,3,5] 因为题目要求是使得所有 小于 x 的节点都出现在 大于或等于 x 的节点之前。所以其实我移动那些数值大的是没有意义的 还有其实测试的时候没跟我说这种情况 就是如果这个x节点不在的话怎么办?

这个代码三就当是我的一个记录吧 在纸上写写画画半天 但是我这种方法肯定是可以的 如何进行修改呢?

1.将左边的凡是大的移动到first_x前面的元素之后就行 当然还需要判断这个first_x之前的这个元素是不是比特定值大的

2.如何解决没有链表中没有特定值的问题 (虽然我其实不太确定题目是不是要求 但是我懒得改这个代码了) 我的想法就是找到比这个特定值大而且是差距最小的那个来充当这个特定值

然后我觉得我做这个题想复杂了 还不如直接开辟两个链条 如果这个元素小于特定值放到链条1上 如果这个元素大于等于特定值就放到链条2上 这样多好啊 都不用再辛辛苦苦去找了 而且相对位置不变 还可以满足题目要求 所以我觉得还是用这个方法

接下来的代码就是使用两条链表去分别插入小于特定值 和大于等于特定值的 然后再进行合并就行 这个思路比我之前写的简单多了 接下来是代码展示 就记住pre1和pre2是拿来遍历的 dummy1和dummy2是不能动的就行 然后一连起来就行了 真的很简单 但是这个很耗费内存

代码4

class ListNode(object):
     def __init__(self, val=0, next=None):
        self.val = val
        self.next = next
class Solution(object):
    def partition(self, head, x):
        dummy1=ListNode(0)
        dummy2=ListNode(0)
        pre1=dummy1
        pre2=dummy2
        while head!=None:
            if head.val 
  

我决定等我哪天对自己原本写的代码有着充分的探索欲的时候回来改改看看内存消耗咋样 虽然我肯定写的是一坨 但是毕竟是我自己写的 我再挖一个坑 过一段时间再填吧 我这个拖延症啊 这就是个记录帖

如果你喜欢这个帖子 请多多点赞收藏吧 你们的喜欢是我更新的最大动力

你可能感兴趣的:(python题目练习,链表,数据结构)