刪除鏈表的倒數第N個節點(三種方法實現)


刪除鏈表的倒數第N個節點

給定一個鏈表,刪除鏈表的倒數第 個節點,並且返回鏈表的頭結點。

 

示例:

 

給定一個鏈表: 1->2->3->4->5, 和 n = 2.

當刪除了倒數第二個節點后,鏈表變為 1->2->3->5.

說明:

給定的 n 保證是有效的。

方法一解題思路:要求刪除倒數第N個節點,可以先設兩個指針同時指向鏈表的第一個節點,一個指針遍歷鏈表統計出總共有多少個節點記為i,用總數減去N,即可以算出要刪除的節點為正數第幾個節點記為index=i-N,讓另一個指針移動到index節點的前一個節點(如果要刪除的節點不是第一個節點)。最后執行刪除操作,如果要刪除的節點為第一個節點,則需要修改頭指針,反之,則直接刪除即可

/*解法一*/
/**
* Definition for singly-linked list.
* struct ListNode {
* int val;
* struct ListNode *next;
* };
*/
struct ListNode* removeNthFromEnd(struct ListNode* head, int n) {
int i = 1, j = i, index = 0;
struct ListNode *p, *ptr;
p = ptr = head;

/*尋找到尾節點*/
while (p->next != NULL)
{
p = p->next;
i++;
}

/*確定要刪除的節點為正數第幾個節點*/
index = i - n + 1;

/*將另一個指針移動到index節點的前一個位置*/
while (j + 1 < index)
{
ptr = ptr->next;
j++;
}
/*刪除操作,判斷要刪除的節點是否為第一個節點*/
if (index != 1)
{
ptr->next = ptr->next->next; 
return head;
}
else
{

return head = ptr->next;
}
}

方法二解題思路:設置兩個指針同時指向第一個節點,讓第一個指針p向前移動n次,之后第二個指針p和指針ptr開始一起移動,直到p為空或者p->next為空,此時指針ptr指向要刪除節點的前一個節點(如果要刪除的不是第一個節點)。如果要刪除的節點為第一個節點,則需要修改頭指針,反之則直接刪除即可。

/*解法二*/
/**
* Definition for singly-linked list.
* struct ListNode {
* int val;
* struct ListNode *next;
* };
*/
struct ListNode* removeNthFromEnd(struct ListNode* head, int n) {
struct ListNode *p, *ptr = p = head;
int i;

/*讓指針p向前走n步*/
while (n-- > 0)
{
p = p->next;
}

/*當指針p走完n步以后,讓指針p和ptr同時向前走,直到p走到最后一個節點,即p->next=NULL,整個過程p和ptr之間相隔n-1個節點*/
while (p&&p->next != NULL)
{
ptr = ptr->next;
p = p->next;
}

/*此時的ptr指向要刪除節點的前一個節點,需要考慮刪除的節點是否為首元節點*/
if (p == NULL)
return head = head->next;
else
{
ptr->next = ptr->next->next;
return head;
}
}

方法三解題思路:方法三和方法四大同小異,首先當front非空時,讓front移動n+1次,之后讓behind跟着front一起移動(front和behind之間相隔n-1個節點),直到front為空。移動結束以后實行刪除操作,刪除操作和方法一和方法二一樣。

struct ListNode * removeNthFromEnd(struct ListNode * head,int n){

struct ListNode* front = head;
struct ListNode* behind = head;

while (front != NULL) {
front = front->next; /*指針front往前移動n+1次*/

if (n-- < 0) behind = behind->next;  /*如果指針behind==0,表明需要刪除的節點為第一個節點*/
}

/*循環過后,兩個指針之間相隔n-1個節點*/
if (n == 0) head = head->next;
else behind->next = behind->next->next;
return head;

以上就是解題心得,如果有錯誤或有疑問歡迎大家指出,大家共同進步。


免責聲明!

本站轉載的文章為個人學習借鑒使用,本站對版權不負任何法律責任。如果侵犯了您的隱私權益,請聯系本站郵箱yoyou2525@163.com刪除。



 
粵ICP備18138465號   © 2018-2025 CODEPRJ.COM