方法1 基本方法 已知要删除倒数第N个节点 可以先遍历链表 求出链表节点个数len 那么需要删除的就是第len-N+1个节点,这样就可以直接删除了。
class Solution {
public:
ListNode* removeNthFromEnd(ListNode* head, int n) {
int len = 1;
ListNode *temp = head;
while(temp != nullptr && temp->next != nullptr){
temp = temp->next;
len++;
}
// 获取节点个数为len
// 已知节点个数为i 需要删掉第i-n+1个节点
int num = len-n+1;
int j = 1;
ListNode *dummy = new ListNode(0);
dummy->next = head;
ListNode *pre = dummy;
ListNode *cur = dummy;
cur = cur->next;
for(j = 1; j < num; j++){
pre = pre->next;
cur = cur->next;
// 把cur挪到第num个节点
}
pre->next = cur->next;
delete cur;
// 删除第num个节点
return dummy->next;
}
};
方法2 双指针 首先,指针1从head开始移动N步 然后新建指针2指向head 开始和指针1共同向前移动 指针1再移动len-N次后 指向NULL 与此同时 指针2移动len-N步 指向倒数第N个节点 即为所求节点 (不需要知道len 指针1指向NULL即为判断条件)
// 返回链表的倒数第 k 个节点
ListNode* findFromEnd(ListNode* head, int k) {
ListNode* p1 = head;
// p1 先走 k 步
for (int i = 0; i < k; i++) {
p1 = p1 -> next;
}
ListNode* p2 = head;
// p1 和 p2 同时走 n - k 步
while (p1 != nullptr) {
p2 = p2 -> next;
p1 = p1 -> next;
}
// p2 现在指向第 n - k + 1 个节点,即倒数第 k 个节点
return p2;
}
参考: