📜  删除链表中间

📅  最后修改于: 2022-05-13 01:57:45.480000             🧑  作者: Mango

删除链表中间

给定一个单向链表,删除链表的中间部分。例如,如果给定的链表是 1->2->3->4->5 那么链表应该修改为 1->2->4->5

如果有偶数个节点,那么就会有两个中间节点,我们需要删除第二个中间元素。例如,如果给定的链表是 1->2->3->4->5->6,则应将其修改为 1->2->3->5->6。
如果输入链表为 NULL,则它应保持为 NULL。

如果输入链表有 1 个节点,则应删除该节点并返回一个新的头。

简单的解决方法:思路是先计算链表中的节点数,然后使用简单的删除过程删除第n/2个节点。

C++14
// C++ program to delete middle
// of a linked list
#include 
using namespace std;
 
/* Link list Node */
struct Node {
    int data;
    struct Node* next;
};
// count of nodes
int countOfNodes(struct Node* head)
{
    int count = 0;
    while (head != NULL) {
        head = head->next;
        count++;
    }
    return count;
}
 
// Deletes middle node and returns
// head of the modified list
struct Node* deleteMid(struct Node* head)
{
    // Base cases
    if (head == NULL)
        return NULL;
    if (head->next == NULL) {
        delete head;
        return NULL;
    }
    struct Node* copyHead = head;
 
    // Find the count of nodes
    int count = countOfNodes(head);
 
    // Find the middle node
    int mid = count / 2;
 
    // Delete the middle node
    while (mid-- > 1) {
        head = head->next;
    }
 
    // Delete the middle node
    head->next = head->next->next;
 
    return copyHead;
}
 
// A utility function to print
// a given linked list
void printList(struct Node* ptr)
{
    while (ptr != NULL) {
        cout << ptr->data << "->";
        ptr = ptr->next;
    }
    cout << "NULL\n";
}
 
// Utility function to create a new node.
Node* newNode(int data)
{
    struct Node* temp = new Node;
    temp->data = data;
    temp->next = NULL;
    return temp;
}
 
/* Driver program to test above function*/
int main()
{
    /* Start with the empty list */
    struct Node* head = newNode(1);
    head->next = newNode(2);
    head->next->next = newNode(3);
    head->next->next->next = newNode(4);
 
    cout << "Given Linked List\n";
    printList(head);
 
    head = deleteMid(head);
 
    cout << "Linked List after deletion of middle\n";
    printList(head);
 
    return 0;
}


Java
// Java program to delete middle
// of a linked list
import java.io.*;
 
class GFG {
 
    /* Link list Node */
    static class Node {
        int data;
        Node next;
    }
 
    // Utility function to create a new node.
    static Node newNode(int data)
    {
        Node temp = new Node();
        temp.data = data;
        temp.next = null;
        return temp;
    }
 
    // count of nodes
    static int countOfNodes(Node head)
    {
        int count = 0;
        while (head != null) {
            head = head.next;
            count++;
        }
        return count;
    }
 
    // Deletes middle node and returns
    // head of the modified list
    static Node deleteMid(Node head)
    {
        // Base cases
        if (head == null)
            return null;
        if (head.next == null) {
            return null;
        }
        Node copyHead = head;
 
        // Find the count of nodes
        int count = countOfNodes(head);
 
        // Find the middle node
        int mid = count / 2;
 
        // Delete the middle node
        while (mid-- > 1) {
            head = head.next;
        }
 
        // Delete the middle node
        head.next = head.next.next;
 
        return copyHead;
    }
 
    // A utility function to print
    // a given linked list
    static void printList(Node ptr)
    {
        while (ptr != null) {
            System.out.print(ptr.data + "->");
            ptr = ptr.next;
        }
        System.out.println("NULL");
    }
 
    /* Driver code*/
    public static void main(String[] args)
    {
        /* Start with the empty list */
        Node head = newNode(1);
        head.next = newNode(2);
        head.next.next = newNode(3);
        head.next.next.next = newNode(4);
 
        System.out.println("Gven Linked List");
        printList(head);
 
        head = deleteMid(head);
 
        System.out.println(
            "Linked List after deletion of middle");
        printList(head);
    }
}
 
// This code is contributed by rajsanghavi9.


Python3
# Python3 program to delete middle
# of a linked list
  
# Link list Node
class Node:
     
    def __init__(self):
         
        self.data = 0
        self.next = None
     
# Count of nodes
def countOfNodes(head):
 
    count = 0
     
    while (head != None):
        head = head.next
        count += 1
     
    return count
 
# Deletes middle node and returns
# head of the modified list
def deleteMid(head):
 
    # Base cases
    if (head == None):
        return None
    if (head.next == None):
        del head
        return None
 
    copyHead = head
  
    # Find the count of nodes
    count = countOfNodes(head)
  
    # Find the middle node
    mid = count // 2
  
    # Delete the middle node
    while (mid > 1):
        mid -= 1
        head = head.next
  
    # Delete the middle node
    head.next = head.next.next
  
    return copyHead
 
# A utility function to print
# a given linked list
def printList(ptr):
 
    while (ptr != None):
        print(ptr.data, end = '->')
        ptr = ptr.next
     
    print('NULL')
     
# Utility function to create a new node.
def newNode(data):
 
    temp = Node()
    temp.data = data
    temp.next = None
    return temp
 
# Driver Code
if __name__=='__main__':
     
    # Start with the empty list
    head = newNode(1)
    head.next = newNode(2)
    head.next.next = newNode(3)
    head.next.next.next = newNode(4)
  
    print("Gven Linked List")
    printList(head)
  
    head = deleteMid(head)
  
    print("Linked List after deletion of middle")
    printList(head)
 
# This code is contributed by rutvik_56


C++
// C++ program to delete middle
// of a linked list
#include 
using namespace std;
 
/* Link list Node */
struct Node {
    int data;
    struct Node* next;
};
 
// Deletes middle node and returns
// head of the modified list
struct Node* deleteMid(struct Node* head)
{
    // Base cases
    if (head == NULL)
        return NULL;
    if (head->next == NULL) {
        delete head;
        return NULL;
    }
 
    // Initialize slow and fast pointers
    // to reach middle of linked list
    struct Node* slow_ptr = head;
    struct Node* fast_ptr = head;
 
    // Find the middle and previous of middle.
// To store previous of slow_ptr   
struct Node* prev;
    while (fast_ptr != NULL
&& fast_ptr->next != NULL) {
        fast_ptr = fast_ptr->next->next;
        prev = slow_ptr;
        slow_ptr = slow_ptr->next;
    }
 
    // Delete the middle node
    prev->next = slow_ptr->next;
    delete slow_ptr;
 
    return head;
}
 
// A utility function to print
// a given linked list
void printList(struct Node* ptr)
{
    while (ptr != NULL) {
        cout << ptr->data << "->";
        ptr = ptr->next;
    }
    cout << "NULL\n";
}
 
// Utility function to create a new node.
Node* newNode(int data)
{
    struct Node* temp = new Node;
    temp->data = data;
    temp->next = NULL;
    return temp;
}
 
/* Driver program to test above function*/
int main()
{
    /* Start with the empty list */
    struct Node* head = newNode(1);
    head->next = newNode(2);
    head->next->next = newNode(3);
    head->next->next->next = newNode(4);
 
    cout << "Given Linked List\n";
    printList(head);
 
    head = deleteMid(head);
 
    cout << "Linked List after deletion of middle\n";
    printList(head);
 
    return 0;
}


Java
// Java program to delete the
// middle of a linked list
class GfG {
 
    /* Link list Node */
    static class Node {
        int data;
        Node next;
    }
 
    // Deletes middle node and returns
    // head of the modified list
    static Node deleteMid(Node head)
    {
        // Base cases
        if (head == null)
            return null;
        if (head.next == null) {
            return null;
        }
 
        // Initialize slow and fast pointers
        // to reach middle of linked list
        Node slow_ptr = head;
        Node fast_ptr = head;
 
        // Find the middle and previous of middle.
        Node prev = null;
 
        // To store previous of slow_ptr
        while (fast_ptr != null
&& fast_ptr.next != null) {
            fast_ptr = fast_ptr.next.next;
            prev = slow_ptr;
            slow_ptr = slow_ptr.next;
        }
 
        // Delete the middle node
        prev.next = slow_ptr.next;
 
        return head;
    }
 
    // A utility function to print
// a given linked list
    static void printList(Node ptr)
    {
        while (ptr != null) {
            System.out.print(ptr.data + "->");
            ptr = ptr.next;
        }
        System.out.println("NULL");
    }
 
    // Utility function to create a new node.
    static Node newNode(int data)
    {
        Node temp = new Node();
        temp.data = data;
        temp.next = null;
        return temp;
    }
 
    /* Driver code*/
    public static void main(String[] args)
    {
        /* Start with the empty list */
        Node head = newNode(1);
        head.next = newNode(2);
        head.next.next = newNode(3);
        head.next.next.next = newNode(4);
 
        System.out.println("Given Linked List");
        printList(head);
 
        head = deleteMid(head);
 
        System.out.println("Linked List after deletion of middle");
        printList(head);
    }
}
 
// This code is contributed by Prerna saini.


Python3
# Python3 program to delete the
# middle of a linked list
 
# Linked List Node
class Node:
     
    def __init__(self, data):
         
        self.data = data
        self.next = None
 
# Create and handle list operations
class LinkedList:
     
    def __init__(self):
         
        # Head of the list
        self.head = None
 
    # Add new node to the list end
    def addToList(self, data):
         
        newNode = Node(data)
        if self.head is None:
            self.head = newNode
            return
             
        last = self.head
         
        while last.next:
            last = last.next
             
        last.next = newNode
 
    # Returns the list in string format
    def __str__(self):
         
        linkedListStr = ""
        temp = self.head
         
        while temp:
            linkedListStr += str(temp.data) + "->"
            temp = temp.next
             
        return linkedListStr + "NULL"
 
    # Method deletes middle node
    def deleteMid(self):
 
        # Base cases
        if (self.head is None or
            self.head.next is None):
            return
 
        # Initialize slow and fast pointers
        # to reach middle of linked list
        slow_Ptr = self.head
        fast_Ptr = self.head
 
        # Find the middle and previous of middle
        prev = None
 
        # To store previous of slow pointer
        while (fast_Ptr is not None and
               fast_Ptr.next is not None):
            fast_Ptr = fast_Ptr.next.next
            prev = slow_Ptr
            slow_Ptr = slow_Ptr.next
 
        # Delete the middle node
        prev.next = slow_Ptr.next
 
# Driver code
linkedList = LinkedList()
 
linkedList.addToList(1)
linkedList.addToList(2)
linkedList.addToList(3)
linkedList.addToList(4)
 
print("Given Linked List")
print(linkedList)
 
linkedList.deleteMid()
 
print("Linked List after deletion of middle")
print(linkedList)
 
# This code is contributed by Debidutta Rath


C#
// C# program to delete middle of a linked list
using System;
 
class GfG {
 
    /* Link list Node */
    class Node {
        public int data;
        public Node next;
    }
 
    // Deletes middle node and returns
    // head of the modified list
    static Node deleteMid(Node head)
    {
        // Base cases
        if (head == null)
            return null;
        if (head.next == null) {
            return null;
        }
 
        // Initialize slow and fast pointers
        // to reach middle of linked list
        Node slow_ptr = head;
        Node fast_ptr = head;
 
        // Find the middle and previous of middle.
        Node prev = null;
 
        // To store previous of slow_ptr
        while (fast_ptr != null && fast_ptr.next != null) {
            fast_ptr = fast_ptr.next.next;
            prev = slow_ptr;
            slow_ptr = slow_ptr.next;
        }
 
        // Delete the middle node
        prev.next = slow_ptr.next;
 
        return head;
    }
 
    // A utility function to print
    // a given linked list
    static void printList(Node ptr)
    {
        while (ptr != null) {
            Console.Write(ptr.data + "->");
            ptr = ptr.next;
        }
        Console.WriteLine("NULL");
    }
 
    // Utility function to create a new node.
    static Node newNode(int data)
    {
        Node temp = new Node();
        temp.data = data;
        temp.next = null;
        return temp;
    }
 
    /* Driver code*/
    public static void Main(String[] args)
    {
        /* Start with the empty list */
        Node head = newNode(1);
        head.next = newNode(2);
        head.next.next = newNode(3);
        head.next.next.next = newNode(4);
 
        Console.WriteLine("Given Linked List");
        printList(head);
 
        head = deleteMid(head);
 
        Console.WriteLine("Linked List after"
                          + "deletion of middle");
        printList(head);
    }
}
 
/* This code is contributed by 29AjayKumar */


Javascript


输出

Given Linked List
1->2->3->4->NULL
Linked List after deletion of middle
1->2->4->NULL

复杂度分析:

  • 时间复杂度: O(n)。
    只需要遍历一次链表
  • 辅助空间: O(1)。
    不需要额外的空间。

有效的解决方案:
做法:上述方案需要对链表进行两次遍历。中间节点可以使用一次遍历删除。这个想法是使用两个指针,slow_ptr 和 fast_ptr。两个指针都从列表的头部开始。当 fast_ptr 到达末尾时,slow_ptr 到达中间。这个想法与本文方法 2 中使用的想法相同。这篇文章中的附加内容是跟踪前一个中间节点,以便可以删除中间节点。

下面是实现。

C++

// C++ program to delete middle
// of a linked list
#include 
using namespace std;
 
/* Link list Node */
struct Node {
    int data;
    struct Node* next;
};
 
// Deletes middle node and returns
// head of the modified list
struct Node* deleteMid(struct Node* head)
{
    // Base cases
    if (head == NULL)
        return NULL;
    if (head->next == NULL) {
        delete head;
        return NULL;
    }
 
    // Initialize slow and fast pointers
    // to reach middle of linked list
    struct Node* slow_ptr = head;
    struct Node* fast_ptr = head;
 
    // Find the middle and previous of middle.
// To store previous of slow_ptr   
struct Node* prev;
    while (fast_ptr != NULL
&& fast_ptr->next != NULL) {
        fast_ptr = fast_ptr->next->next;
        prev = slow_ptr;
        slow_ptr = slow_ptr->next;
    }
 
    // Delete the middle node
    prev->next = slow_ptr->next;
    delete slow_ptr;
 
    return head;
}
 
// A utility function to print
// a given linked list
void printList(struct Node* ptr)
{
    while (ptr != NULL) {
        cout << ptr->data << "->";
        ptr = ptr->next;
    }
    cout << "NULL\n";
}
 
// Utility function to create a new node.
Node* newNode(int data)
{
    struct Node* temp = new Node;
    temp->data = data;
    temp->next = NULL;
    return temp;
}
 
/* Driver program to test above function*/
int main()
{
    /* Start with the empty list */
    struct Node* head = newNode(1);
    head->next = newNode(2);
    head->next->next = newNode(3);
    head->next->next->next = newNode(4);
 
    cout << "Given Linked List\n";
    printList(head);
 
    head = deleteMid(head);
 
    cout << "Linked List after deletion of middle\n";
    printList(head);
 
    return 0;
}

Java

// Java program to delete the
// middle of a linked list
class GfG {
 
    /* Link list Node */
    static class Node {
        int data;
        Node next;
    }
 
    // Deletes middle node and returns
    // head of the modified list
    static Node deleteMid(Node head)
    {
        // Base cases
        if (head == null)
            return null;
        if (head.next == null) {
            return null;
        }
 
        // Initialize slow and fast pointers
        // to reach middle of linked list
        Node slow_ptr = head;
        Node fast_ptr = head;
 
        // Find the middle and previous of middle.
        Node prev = null;
 
        // To store previous of slow_ptr
        while (fast_ptr != null
&& fast_ptr.next != null) {
            fast_ptr = fast_ptr.next.next;
            prev = slow_ptr;
            slow_ptr = slow_ptr.next;
        }
 
        // Delete the middle node
        prev.next = slow_ptr.next;
 
        return head;
    }
 
    // A utility function to print
// a given linked list
    static void printList(Node ptr)
    {
        while (ptr != null) {
            System.out.print(ptr.data + "->");
            ptr = ptr.next;
        }
        System.out.println("NULL");
    }
 
    // Utility function to create a new node.
    static Node newNode(int data)
    {
        Node temp = new Node();
        temp.data = data;
        temp.next = null;
        return temp;
    }
 
    /* Driver code*/
    public static void main(String[] args)
    {
        /* Start with the empty list */
        Node head = newNode(1);
        head.next = newNode(2);
        head.next.next = newNode(3);
        head.next.next.next = newNode(4);
 
        System.out.println("Given Linked List");
        printList(head);
 
        head = deleteMid(head);
 
        System.out.println("Linked List after deletion of middle");
        printList(head);
    }
}
 
// This code is contributed by Prerna saini.

蟒蛇3

# Python3 program to delete the
# middle of a linked list
 
# Linked List Node
class Node:
     
    def __init__(self, data):
         
        self.data = data
        self.next = None
 
# Create and handle list operations
class LinkedList:
     
    def __init__(self):
         
        # Head of the list
        self.head = None
 
    # Add new node to the list end
    def addToList(self, data):
         
        newNode = Node(data)
        if self.head is None:
            self.head = newNode
            return
             
        last = self.head
         
        while last.next:
            last = last.next
             
        last.next = newNode
 
    # Returns the list in string format
    def __str__(self):
         
        linkedListStr = ""
        temp = self.head
         
        while temp:
            linkedListStr += str(temp.data) + "->"
            temp = temp.next
             
        return linkedListStr + "NULL"
 
    # Method deletes middle node
    def deleteMid(self):
 
        # Base cases
        if (self.head is None or
            self.head.next is None):
            return
 
        # Initialize slow and fast pointers
        # to reach middle of linked list
        slow_Ptr = self.head
        fast_Ptr = self.head
 
        # Find the middle and previous of middle
        prev = None
 
        # To store previous of slow pointer
        while (fast_Ptr is not None and
               fast_Ptr.next is not None):
            fast_Ptr = fast_Ptr.next.next
            prev = slow_Ptr
            slow_Ptr = slow_Ptr.next
 
        # Delete the middle node
        prev.next = slow_Ptr.next
 
# Driver code
linkedList = LinkedList()
 
linkedList.addToList(1)
linkedList.addToList(2)
linkedList.addToList(3)
linkedList.addToList(4)
 
print("Given Linked List")
print(linkedList)
 
linkedList.deleteMid()
 
print("Linked List after deletion of middle")
print(linkedList)
 
# This code is contributed by Debidutta Rath

C#

// C# program to delete middle of a linked list
using System;
 
class GfG {
 
    /* Link list Node */
    class Node {
        public int data;
        public Node next;
    }
 
    // Deletes middle node and returns
    // head of the modified list
    static Node deleteMid(Node head)
    {
        // Base cases
        if (head == null)
            return null;
        if (head.next == null) {
            return null;
        }
 
        // Initialize slow and fast pointers
        // to reach middle of linked list
        Node slow_ptr = head;
        Node fast_ptr = head;
 
        // Find the middle and previous of middle.
        Node prev = null;
 
        // To store previous of slow_ptr
        while (fast_ptr != null && fast_ptr.next != null) {
            fast_ptr = fast_ptr.next.next;
            prev = slow_ptr;
            slow_ptr = slow_ptr.next;
        }
 
        // Delete the middle node
        prev.next = slow_ptr.next;
 
        return head;
    }
 
    // A utility function to print
    // a given linked list
    static void printList(Node ptr)
    {
        while (ptr != null) {
            Console.Write(ptr.data + "->");
            ptr = ptr.next;
        }
        Console.WriteLine("NULL");
    }
 
    // Utility function to create a new node.
    static Node newNode(int data)
    {
        Node temp = new Node();
        temp.data = data;
        temp.next = null;
        return temp;
    }
 
    /* Driver code*/
    public static void Main(String[] args)
    {
        /* Start with the empty list */
        Node head = newNode(1);
        head.next = newNode(2);
        head.next.next = newNode(3);
        head.next.next.next = newNode(4);
 
        Console.WriteLine("Given Linked List");
        printList(head);
 
        head = deleteMid(head);
 
        Console.WriteLine("Linked List after"
                          + "deletion of middle");
        printList(head);
    }
}
 
/* This code is contributed by 29AjayKumar */

Javascript


输出
Given Linked List
1->2->3->4->NULL
Linked List after deletion of middle
1->2->4->NULL

复杂度分析:

  • 时间复杂度: O(n)。
    只需要遍历一次链表
  • 辅助空间: O(1)。
    因为不需要额外的空间。

如果您希望与专家一起参加现场课程,请参阅DSA 现场工作专业课程学生竞争性编程现场课程