[24].兩兩交換鏈表中的節點

 


題目

給定一個鏈表,兩兩交換其中相鄰的節點,並返回交換後的鏈表。

你不能只是單純的改變節點內部的值,而是需要實際的進行節點交換。

示例:

給定 1->2->3->4, 你應該返回 2->1->4->3.

 


函數原型

C 的函數原型:

struct ListNode* swapPairs(struct ListNode* head){

}

 


邊界判斷

struct ListNode* swapPairs(struct ListNode* head){

}

 


算法設計:哨兵

思路:好的結構設計,可以簡化算法。按照常規的刪除方法,釋放很多元素都適用,但交換第一個元素,需要特殊處理。更好的方法,是採用哨兵實現通用化。

這裏有 4 個指針,而後交換這 4 個指針就可以交換前後的元素。

交換步驟:

typedef struct ListNode Node;
struct ListNode* swapPairs(struct ListNode* head){
    // 創建哨兵
    Node* sentinel = malloc( sizeof(Node) );
    sentinel->next = head;  

    Node *p = sentinel;
    while( p->next && p->next->next ){  // 倆個結點都存在
        Node *node1 = p->next;
        Node *node2 = p->next->next;
        Node *next = node2->next;
        
        //swap(p, node1, node2);
        node2->next = node1;
        node1->next = next;
        p->next = node2;

        p = node1;
    }
    Node *ans = sentinel->next;
    free(sentinel), sentinel = NULL;

    return ans;
}
  • 時間複雜度:Θ(n)\Theta(n)
  • 空間複雜度:Θ(1)\Theta(1)

 


算法設計:遞歸

struct ListNode* swapPairs(struct ListNode* head){
    struct ListNode* pTmpNode = NULL;

    if ( head == NULL || head->next == NULL ) {
        return head;
    } else {
        //2. 交換操作
        pTmpNode = head->next;
        head->next = pTmpNode->next;
        pTmpNode->next = head;
        head = pTmpNode;
    }
        //3. 遞歸函數
        head->next->next = swapPairs(head->next->next);
        return head;
}
  • 時間複雜度:Θ(n)\Theta(n)
  • 空間複雜度:Θ(n)\Theta(n)
發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章