鏈表算法題

一、反轉鏈表

力扣地址指針

實現方法一:三指針遍歷,pre+cur+next;時間複雜度O(n),空間複雜度O(1)。

func reverseList(head *ListNode) *ListNode {
    var pre *ListNode
    cur := head
    for cur != nil {
        next := cur.Next
        cur.Next = pre
        pre = cur
        cur = next
    }

    return pre
}

實現方法二:遞歸解法,1+ (reverse(2,3));時間複雜度O(n),空間複雜度O(n)(遞歸調用要佔用系統棧空間)。

func reverseList(head *ListNode) *ListNode {
    //1.遞歸結束
    if head == nil || head.Next == nil{
        return head
    }
    //2.遞歸主體
    newHead := reverseList(head.Next)
    head.Next.Next = head
    head.Next = nil
    return newHead
}

二、刪除鏈表的節點

力扣地址code

解法:增長dummyHead,把刪除頭尾節點的特殊狀況,變成了普通狀況。

func removeElements(head *ListNode, val int) *ListNode {
    dummyHead := &ListNode{}
    dummyHead.Next = head
    cur := dummyHead
    for cur.Next != nil{
        if cur.Next.Val == val{
            cur.Next = cur.Next.Next
        }else{
            cur = cur.Next
        }   
    }
    return dummyHead.Next
}

三、合併兩個有序單向鏈表

力扣地址遞歸

func mergeTwoLists(l1 *ListNode, l2 *ListNode) *ListNode {
    dummyHead := &ListNode{}
    cur := dummyHead
    for l1 != nil && l2 != nil{
        if l1.Val <= l2.Val{
            cur.Next = l1
            cur = l1
            l1 = l1.Next
        }else{
            cur.Next = l2
            cur = l2
            l2 = l2.Next
        }
    }
    cur.Next = l1
    if l1 == nil {
        cur.Next = l2
    }

    return dummyHead.Next
}
相關文章
相關標籤/搜索