【LeetCode】—— 链表面试题(上)

LeetCode 203题 移除链表元素

题目描述

删除链表中等于给定值 val 的全部节点。
示例:web

输入: 1->2->6->3->4->5->6, val = 6
输出: 1->2->3->4->5

解题思想

首先能够将本题分为三类状况来处理:
一、链表为空时,即head == NULL,直接返回0
二、链表中只有一个元素时,判断该元素是否是所要找的值为val的元素,若是是直接删除,不然不作处理
三、链表有多个元素时,定义一个指针cur,只要cur->next不为空,让cur一直走寻找链表中是否是有值为val的元素,这里为了方便删除值为val的节点,我判断cur->next的值是否为val,如果让cur->next = cur->next->next可直接删除该节点。svg

代码实现

struct ListNode* removeElements(struct ListNode* head, int val) {
    struct ListNode *cur;
    if(head == NULL)
        return 0;
    while(head != NULL && head->val == val)
        head = head->next;
    if(head == NULL)
        return 0;
    cur = head;
    while(cur->next != NULL)
    {
        if(cur->next->val == val)
           cur->next = cur->next->next;
        else
            cur = cur->next;
    }
    return head;
}

LeetCode 206题 反转链表

题目描述

反转一个单链表。3d

示例:指针

输入: 1->2->3->4->5->NULL
输出: 5->4->3->2->1->NULL

解题思想

反转链表

代码实现

struct ListNode* reverseList(struct ListNode* head) {
    
    struct ListNode* newhead=NULL;
    struct ListNode* cur=head;
    while(cur!=NULL)
    {
        //保存cur的下一 个节点
        struct ListNode*next=cur->next;
         
        //头插
        cur->next=newhead;
        newhead=cur;
    
    cur=next;
}

 return newhead;
}

LeetCode 879题 链表的中间节点

题目描述

给定一个带有头结点 head 的非空单链表,返回链表的中间结点。code

若是有两个中间结点,则返回第二个中间结点。
示例 1:xml

输入:[1,2,3,4,5]
输出:此列表中的结点 3 (序列化形式:[3,4,5])
返回的结点值为 3 。 (测评系统对该结点序列化表述是 [3,4,5])。

注意,咱们返回了一个 ListNode 类型的对象 ans,这样:
ans.val = 3, ans.next.val = 4, ans.next.next.val = 5, 以及 ans.next.next.next = NULL.

示例 2:对象

输入:[1,2,3,4,5,6]
输出:此列表中的结点 4 (序列化形式:[4,5,6])
因为该列表有两个中间结点,值分别为 3 和 4,咱们返回第二个结点。

解题思想

  • 定义两个指针,一个快指针fast,一个慢指针slow,快指针一次走两步,慢指针一次走一步,当快指针走到最后,慢指针正好走在中间的位置,此时返回慢指针所在位置便可,注意当链表为空时直接返回头结点便可。

代码实现

struct ListNode* middleNode(struct ListNode* head) {
    if(head == NULL || head->next == NULL)
        return head;
    struct ListNode* fast = head;
    struct ListNode* slow = head;
    while(fast != NULL && fast->next !=NULL)
    {
        fast = fast->next->next;
        slow = slow->next;
    }
    return slow;  
}

LeetCode 19题 删除链表中的倒数第n个节点

题目描述

给定一个链表,删除链表的倒数第 n 个节点,而且返回链表的头结点。blog

示例:rem

给定一个链表: 1->2->3->4->5, 和 n = 2.
当删除了倒数第二个节点后,链表变为 1->2->3->5.

解题思路

定义两个指针,一个快指针fast,一个慢指针slow,让快指针先走n步,再让快慢指针一块儿走,当快指针走到链表最后,慢指针正好走在链表的倒数第n-1个位置,此时删除slow指针的后一个值,即删除了链表第n个位置的值,再考虑一些特殊状况,好比链表只有一个值时,可以让slow->next = slow->next->next,删除以后,这时链表为空。it

代码实现

struct ListNode* removeNthFromEnd(struct ListNode* head, int n) {
     int i=0;
    struct ListNode* slow,* fast = head;
    slow = (struct ListNode*)malloc(sizeof(struct ListNode));
    slow->next = head;
    while(i < n)
    {
        fast = fast -> next;
        i++;
    }
    while(fast != NULL)
    {
        fast = fast -> next;
        slow = slow -> next;
    }
    if(slow -> next == head)
        return head -> next;
    else
        slow->next = slow->next ->next;
        return head;
}