这道题要求用空间复杂度为O(1)的算法,不用额外的数组空间,显然一定是对单链表的逆置,408对这点考察的频率特别高,需要多加锻炼,以及默写快排。
#include<bits/stdc++.h>
using namespace std;
typedef struct node {
int data;
struct node* next;
}NODE;
// 将链表的后半段逆置以后插入前半段
void change_list(NODE* h) {
NODE *fast,*low,*s,*r;
low = fast = h;
while(fast -> next != NULL) {
low = low -> next;
fast = fast -> next;
if (fast -> next != NULL) {
fast = fast -> next;
}
}
fast = low -> next; // low所指向的结点即为中间结点,fast为后半段链表的首结点
low -> next = NULL;
while(fast != NULL) {
r = fast -> next;
fast -> next = low -> next;
low -> next = fast;
fast = r;
}
s = h -> next; // s指向前半段的第一个数据结点,即从这里开始插入
fast = low -> next; // 从后半段开始插入
low -> next = NULL;
while(fast != NULL) {
r = fast -> next; // 1 --> 2 --> 3 ---> 4 ---> 7 ----> 6 ----> 5
fast -> next = low -> next;
low -> next = fast; // 1 --> 7 ---> 2
low = fast -> next; // low = 7 -> next == 2 再从2号结点的位置开始插入
fast = r; // 之前暂存的结点用来保留fast的下一个指针
}
}