{x}
blog image

Reverse Linked List II

Given the head of a singly linked list and two integers left and right where left <= right, reverse the nodes of the list from position left to position right, and return the reversed list.

 

Example 1:

Input: head = [1,2,3,4,5], left = 2, right = 4
Output: [1,4,3,2,5]

Example 2:

Input: head = [5], left = 1, right = 1
Output: [5]

 

Constraints:

  • The number of nodes in the list is n.
  • 1 <= n <= 500
  • -500 <= Node.val <= 500
  • 1 <= left <= right <= n

 

Follow up: Could you do it in one pass?

Solution Explanation: Reversing a Linked List II

This problem requires reversing a portion of a singly linked list between indices left and right (inclusive). The solution uses a simulation approach with a dummy head node for efficient manipulation.

Algorithm:

  1. Dummy Node: A dummy node is created and prepended to the original linked list. This simplifies handling the edge case where the reversal starts at the head of the list.

  2. Find the Start: The code iterates to find the node at position left - 1 (the node before the reversal starts). This node is stored in pre.

  3. Reverse Sublist: The code then reverses the sublist from left to right using iterative reversal. It keeps track of three pointers:

    • pre: Points to the node before the sublist to be reversed.
    • cur: The current node being processed in the sublist.
    • t: Temporarily stores the next node to avoid losing it during the reversal.
  4. Reconnect: After reversing the sublist, the code reconnects the reversed sublist to the rest of the list. It updates the next pointers of the nodes at positions left -1 and right + 1.

  5. Return: The function returns the next node of the dummy node (which is the head of the modified linked list).

Time and Space Complexity:

  • Time Complexity: O(n) - The code iterates through the linked list at most twice: once to find the starting point and once to reverse the sublist. n represents the length of the linked list.

  • Space Complexity: O(1) - The solution uses a constant amount of extra space regardless of the input list size.

Code Explanation (Python3 as example, but principles apply across all languages):

class Solution:
    def reverseBetween(self, head: ListNode, left: int, right: int) -> ListNode:
        # Handle empty or single-node list, or when left and right are the same.
        if not head or not head.next or left == right:
            return head
 
        dummy = ListNode(0, head)  # Dummy node for easier handling
        pre = dummy
        for _ in range(left - 1):  # Find the node before the sublist
            pre = pre.next
 
        # Reverse the sublist
        p, q = pre, pre.next  #p is the node before the reversed part, q is the first node to be reversed
        cur = q
        for _ in range(right - left + 1):
            t = cur.next  #Store next node to avoid losing it
            cur.next = pre # Reverse the link
            pre, cur = cur, t  # Move pointers
 
        # Reconnect the reversed sublist
        p.next = pre #Connect the sublist from behind
        q.next = cur  # Connect the sublist from the front
 
        return dummy.next  # Return the head of the modified list

The other language implementations follow the same logic with syntactic variations for each language. The key aspects – dummy node, iterative reversal, and reconnection – remain consistent.