[C language] review of linked list questions of LeetCode

Keywords: C Singly Linked List

preface

  • Because the freshman learned the linked list hastily and did very little about some algorithm problems of the linked list, the basic knowledge of the linked list tree graph became worse and worse during the last semester of sophomore year, let alone the algorithm problems of tree and graph. So after finishing a project in the direction of iOS last week, I chose to use this free time to re consolidate the foundation. After all, I will take the algorithm for internship, job interview and HKCEE in the future.
  • Here are some basic but important topics of the linked list done this week

LeetCode 206. Reverse linked list

LeetCode 206. Reverse linked list

  • Method 1: iterative method

When traversing the linked list, change the next pointer of the current node to point to the previous node. Since a node does not reference its previous node, its previous node must be stored in advance. The latter node also needs to be stored before changing the reference. Finally, a new header reference is returned.

/**
 * Definition for singly-linked list.
 * struct ListNode {
 *     int val;
 *     struct ListNode *next;
 * };
 */

struct ListNode* reverseList(struct ListNode* head){
    struct ListNode* p = NULL;
    struct ListNode* cur = head;
    if (!cur) {
        return head;
    }
    while (cur) {
        struct ListNode* pNext = cur->next;
        cur->next = p;
        p = cur;
        cur = pNext;
    }
    return p;
}
  • Method 2: recursive method

If the node from Nk+1 to Nm has been reversed and we are in Nk, we want the next node of Nk+1 to point to Nk,
Therefore, Nk.next.next = Nk;
Note that the next node of N1 must point to ∅. If this is ignored, links may be generated in the linked list.

/**
 * Definition for singly-linked list.
 * struct ListNode {
 *     int val;
 *     struct ListNode *next;
 * };
 */

struct ListNode* reverseList(struct ListNode* head){
    if (!head || !head->next) {
        return head;
    }
    struct ListNode* realHead = reverseList(head->next);
    head->next->next = head;
    head->next = NULL;

    return realHead;
}

LeetCode 143. Rearrange linked list

LeetCode 143. Rearrange linked list

  • Method 1: the time complexity of the method I use is a little high. I use double pointers. The first pointer stays at the previous node at position 2 as shown in the figure above, and then the second pointer traverses backward from the first pointer until the next - > next of the second pointer is NULL, indicating that it is necessary to move the node pointed to by the second pointer to the back of the first pointer. After the insertion, the first pointer moves back twice (why twice? Because a new node has been inserted just now), and then cycle as above until the next of the first pointer is empty.
/**
 * Definition for singly-linked list.
 * struct ListNode {
 *     int val;
 *     struct ListNode *next;
 * };
 */

void reorderList(struct ListNode* head){
    struct ListNode* pSlow = head;
    struct ListNode* pFast = head;
    if (!head->next || !head->next || !head->next->next) {
        return head;
    }
    while (pSlow->next && pSlow->next->next) {
        pFast = pSlow;
        while (pFast->next->next) {
            pFast = pFast->next;
        }
        struct ListNode* pTemp1 = pFast->next;
        pFast->next = pFast->next->next;
        struct ListNode* pTemp3 = pSlow->next;
        pSlow->next = pTemp1;
        pTemp1->next = pTemp3;
        pSlow = pSlow->next->next;
    }
    return head;
}
  • Official method:

Method 2: linear table
Method 3: find the midpoint of the linked list + reverse order of the linked list + merge the linked list
Official practice

LeetCode 142. Ring linked list II

LeetCode 142. Ring linked list II

  • Problem solution

After looking at the solution of the problem, I found that it mainly embodies the idea of mathematics. Through the relationship between the distance traveled after the fast and slow pointers meet, I listed an equation. The slow pointer continues to walk, and then it is introduced that the third pointer starts to walk from the head. When the slow pointer happens to walk to the index, the third pointer also goes to the index, It can be judged that the location of the encounter is the requested index node.

/**
 * Definition for singly-linked list.
 * struct ListNode {
 *     int val;
 *     struct ListNode *next;
 * };
 */
struct ListNode *detectCycle(struct ListNode *head) {
    struct ListNode *pSlow = head;
    struct ListNode *pFast = head;
    if (!pSlow || !pSlow->next) {
        return NULL;
    }
    int flag = 0;
    while (flag == 0 || pSlow != pFast) {
        if (!pFast || !pFast->next){
            return NULL;
        }
        flag = 1;
        pFast = pFast->next->next;
        pSlow = pSlow->next;
    }
    struct ListNode *ptr = head;
    while (ptr != pSlow) {
        ptr = ptr->next;
        pSlow = pSlow->next;
    }
    return pSlow;
}
  • Continue to practice LeetCode next week and learn about the algorithm of tree

Posted by sfx81 on Sat, 20 Nov 2021 17:27:53 -0800