题目链接

  题目要求:

  Given a singly linked list LL0→L1→…→Ln-1→Ln,
  reorder it to: L0→LnL1→Ln-1→L2→Ln-2→…

  You must do this in-place without altering the nodes' values.

  For example,
  Given {1,2,3,4}, reorder it to {1,4,2,3}.

  刚看到题目,第一个冒出来的想法如下:

  LeetCode之“链表”:Reorder List_LeetCode

  对应程序如下:

LeetCode之“链表”:Reorder List_逆序_02LeetCode之“链表”:Reorder List_链表反转_03
 1 /**
 2  * Definition for singly-linked list.
 3  * struct ListNode {
 4  *     int val;
 5  *     ListNode *next;
 6  *     ListNode(int x) : val(x), next(NULL) {}
 7  * };
 8  */
 9 class Solution {
10 public:
11     void reorderList(ListNode* head) {
12         if (!head || !head->next || !head->next->next)
13             return;
14     
15         ListNode *start = head, *end = nullptr;
16         bool flag = true;
17         while (start->next && start->next->next)
18         {
19             if (flag)
20                 head = start;
21             flag = false;
22     
23             end = start;
24             auto preEnd = end;
25             while (end->next)
26             { 
27                 preEnd = end;
28                 end = end->next;
29             }
30             
31             preEnd->next = nullptr;
32             auto next = start->next;
33             start->next = end;
34             end->next = next;
35     
36             start = next;
37         }
38     }
39 };
View Code

  但超时了!!!

  后来参考了网上别人的通用解法:

  1)用快慢指针找到中间节点,将链表分成两部分。

  2)对后面一半的链表逆序,这个也是常见的问题了(链表反转)。

  3)合并两个链表。

  具体程序如下(72ms):

 1 /**
 2  * Definition for singly-linked list.
 3  * struct ListNode {
 4  *     int val;
 5  *     ListNode *next;
 6  *     ListNode(int x) : val(x), next(NULL) {}
 7  * };
 8  */
 9 class Solution {
10 public:
11     void reorderList(ListNode* head) {
12         if (!head || !head->next || !head->next->next)
13             return;
14     
15         ListNode *slow = head, *fast = head;
16         while(fast->next && fast->next->next)
17         {
18             slow = slow->next;
19             fast = fast->next->next;
20         }
21         
22         ListNode *mid = slow->next;
23         ListNode *prev = nullptr;
24         while(mid)
25         {
26             ListNode *next = mid->next;
27             mid->next = prev;
28             prev = mid;
29             mid = next;
30         }
31         slow->next = nullptr;
32         
33         ListNode *start = head;
34         bool flag = true;
35         while (start && prev)
36         {
37             ListNode *next = start->next;
38             start->next = prev;
39             prev = prev->next;
40             start->next->next = next;
41     
42             if (flag)
43                 head = start;
44             flag = false;
45     
46             start = next;
47         }
48         
49     }
50 };