给你单链表的头指针 head
和两个整数 left
和 right
,其中 left <= right
。请你反转从位置 left
到位置 right
的链表节点,返回 反转后的链表 。
示例 1:
输入:head = [1,2,3,4,5], left = 2, right = 4 输出:[1,4,3,2,5]
示例 2:
输入:head = [5], left = 1, right = 1 输出:[5]
提示:
- 链表中节点数目为
n
1 <= n <= 500
-500 <= Node.val <= 500
1 <= left <= right <= n
思路:
1.如果left==right说明左与右相同,不需要进行逆转,则返回单链表head为头结点。
2.如果不同,我们就需要虚拟一个新结点,让它指向头结点
虚拟头结点 头结点 p:目的是找到left的前一个,q是找到第right个,我们让s指向p->next,即为我们想要先处理的数据,让p->next与s->next连接,s出来,s->next与q->next连接,q->next与s连接实现插入,那么s位置就挪到了q的后面,根据左与右之间的距离差来实现循环次数,即可完成逆置。
代码:
/**
* Definition for singly-linked list.
* struct ListNode {
* int val;
* struct ListNode *next;
* };
*/
struct ListNode* reverseBetween(struct ListNode* head, int left, int right) {
if(left==right){
return head;
}
else{
struct ListNode*hhead;
hhead=malloc(sizeof(struct ListNode));
hhead->next=head;
struct ListNode *p,*q,*s;
p=hhead;
q=hhead;
int i;
for(i=0;i<left-1;i++){
p=p->next;
}
for(i=0;i<right;i++){
q=q->next;
}
for(i=0;i<right-left;i++){
s=p->next;
p->next=s->next;
s->next=q->next;
q->next=s;
}
return hhead->next;
}
}