1. 程式人生 > >#leetcode刷題之路25- k個一組翻轉鏈表

#leetcode刷題之路25- k個一組翻轉鏈表

而是 The 總數 while循環 main 繼續 nullptr 之前 node

給出一個鏈表,每 k 個節點一組進行翻轉,並返回翻轉後的鏈表。
k 是一個正整數,它的值小於或等於鏈表的長度。如果節點總數不是 k 的整數倍,那麽將最後剩余節點保持原有順序。

示例 :
給定這個鏈表:1->2->3->4->5
當 k = 2 時,應當返回: 2->1->4->3->5
當 k = 3 時,應當返回: 3->2->1->4->5

說明 :
你的算法只能使用常數的額外空間。
你不能只是單純的改變節點內部的值,而是需要實際的進行節點交換。

思路:先把是不是從頭開始區分一下,然後每一次翻轉之前,都要判斷數量夠不夠k

#include <iostream>
using namespace std;
struct ListNode {
    int val;
    ListNode *next;
    ListNode(int x) : val(x), next(NULL) {}
};

ListNode* createlist(int n)//生成鏈表
{
    if (n == 0) return nullptr;
    ListNode* head = (ListNode*)malloc(sizeof(ListNode));
    cin >> head->val;
    ListNode
* pre = head; for (int i = 0; i < n - 1; i++) { ListNode* p = (ListNode*)malloc(sizeof(ListNode)); cin >> p->val; pre->next = p; pre = pre->next; } pre->next = nullptr; return head; } ListNode* reverselist(ListNode* head, ListNode *p, int
k) { int tk = k;//暫時保存k的值 if (head == p)//是頭 { ListNode* temp = head;// ListNode* endd = head;// ListNode* ttemp=nullptr; ListNode* pre = nullptr;//保存已反轉的下一個 ListNode* end = nullptr;// ListNode* t = head;//保存反轉過的最後一個 while (tk > 0)//說明從頭節點開始有K個節點可供反轉 { if (temp != nullptr) { temp = temp->next; tk--; } else return head; }//while循環後temp指針指向鏈表的第K+1個節點 //cout<<temp->val<<endl; //開始反轉,讓頭指向空 pre = head->next; head->next = nullptr; //cout<<temp->val<<endl; while (pre != temp) { //t = pre; end = pre->next; pre->next = head; head = pre; pre = end; } //cout << t->val << endl; endd->next = temp;//連接後面剩下的 //帶頭的前k個處理完了,判斷接下來的夠不夠k個 tk = k; //temp = t; while (tk != 0)//是否可繼續處理 { if (temp != nullptr) { temp = temp->next; tk--; } else return head; } //cout << t->val <<t->next->val<< endl; //cout << head->val << head->next->val << endl; reverselist(head, t, k);//夠的話就遞歸反轉 } else { ListNode* pre = p;//保存已經反轉過的最後一個-------------------- ListNode*cur = pre->next;//保存待反轉的第一個 ListNode* cur_next=cur->next ;//保存待反轉的下一個 ListNode* end = nullptr;//存放待反轉的最後一個節點的下一個節點---------------------- ListNode* thead=nullptr;//存放轉後的頭節點--------------- ListNode* tcur = cur_next->next;//存放當前的cur_next的下一個節點,即下次要反轉的那個------------------ ListNode* temp = nullptr;//記錄反轉的鏈表尾 ListNode* t = nullptr;// //-----------------------------先反轉第一次 cur_next->next = cur; cur->next = nullptr; temp = cur; thead = cur_next; tk = k-2; while (tk > 0) { cur = tcur; tcur = tcur->next; cur->next = thead; thead = cur; tk--; } pre->next = thead; temp->next = tcur; t = temp->next; //帶頭的前k個處理完了,判斷接下來的夠不夠k個 tk = k; //temp = t; while (tk != 0)//是否可繼續處理 { if (t != nullptr) { t = t->next; tk--; } else return head; } reverselist(head, temp, k);//夠的話就遞歸反轉 } return head; } ListNode* reverseKGroup(ListNode* head, int k) { if (head == nullptr || k == 0 || k == 1) return head; ListNode *temp = head; head = reverselist(head, head, k); return head; } int main() { ListNode* head = createlist(4); ListNode*ans = reverseKGroup(head, 2); while (ans != nullptr) { cout << ans->val << endl; ans = ans->next; } return 0; }

#leetcode刷題之路25- k個一組翻轉鏈表