Given the head of a singly linked list and two integers X and val, insert a node with value val before the node with value X in the linked list and return the head of the modified list.
Input: head -> 1 -> 2 -> 3, X = 2, val = 5
Output: head -> 1 -> 5 -> 2 -> 3
Explanation: The node with value 5 was added before the node with value 2
Input: head -> 1 -> 2 -> 3, X = 7, val = 5
Output: head -> 1 -> 2 -> 3
Explanation: No node was added as X was not found in the list.
Input: head -> 1, X = 1, val = 10
#include <bits/stdc++.h>
using namespace std;
// Definition of singly linked list
struct ListNode
{
int val;
ListNode *next;
ListNode(int data1)
{
val = data1;
next = NULL;
}
ListNode(int data1, ListNode *next1)
{
val = data1;
next = next1;
}
};
// Solution class
class Solution {
public:
// Function to insert a new node before the given node
ListNode* insertBeforeX(ListNode* &head, int X, int val) {
if (head == NULL) {
return NULL;
}
/* Insert at the beginning if the
value matches the head's data */
if (head->val == X)
return new ListNode(val, head);
ListNode* temp = head;
while (temp->next != NULL) {
/* Insert at the current position if the
next node has the desired value */
if (temp->next->val == X) {
ListNode* newNode = new ListNode(val, temp->next);
temp->next = newNode;
break;
}
temp = temp->next;
}
return head;
}
};
// Helper Function to print the linked list
void printLL(ListNode* head) {
while (head != NULL) {
cout << head->val << " ";
head = head->next;
}
cout << endl;
}
int main() {
// Create a linked list from a vector
vector<int> arr = {1, 2, 4, 5};
int X = 4, val = 3;
ListNode* head = new ListNode(arr[0]);
head->next = new ListNode(arr[1]);
head->next->next = new ListNode(arr[2]);
// Print the original list
cout << "Original List: ";
printLL(head);
// Create a Solution object
Solution sol;
head = sol.insertBeforeX(head, X, val);
// Print the modified linked list
cout << "List after inserting a new node before the given node: ";
printLL(head);
return 0;
}
import java.util.*;
// Definition of singly linked list
class ListNode {
int val;
ListNode next;
ListNode(int data1) {
val = data1;
next = null;
}
ListNode(int data1, ListNode next1) {
val = data1;
next = next1;
}
}
// Solution class
class Solution {
// Function to insert a new node before the given node
public ListNode insertBeforeX(ListNode head, int X, int val) {
if (head == null) {
return null;
}
/* Insert at the beginning if the
value matches the head's data */
if (head.val == X)
return new ListNode(val, head);
ListNode temp = head;
while (temp.next != null) {
/* Insert at the current position if
the next node has the desired value */
if (temp.next.val == X) {
ListNode newNode = new ListNode(val, temp.next);
temp.next = newNode;
break;
}
temp = temp.next;
}
return head;
}
}
// Main class
class Main {
// Helper Function to print the linked list
private static void printLL(ListNode head) {
while (head != null) {
System.out.print(head.val + " ");
head = head.next;
}
System.out.println();
}
// main method
public static void main(String[] args) {
// Create a linked list from an array
int[] arr = {1, 2, 4, 5};
int X = 4, val = 3;
ListNode head = new ListNode(arr[0]);
head.next = new ListNode(arr[1]);
head.next.next = new ListNode(arr[2]);
// Print the original list
System.out.print("Original List: ");
printLL(head);
// Create a Solution object
Solution sol = new Solution();
head = sol.insertBeforeX(head, X, val);
// Print the modified linked list
System.out.print("List after inserting a new node before the given node: ");
printLL(head);
}
}
# Definition of singly linked list
class ListNode:
def __init__(self, val=0, next=None):
self.val = val
self.next = next
class Solution:
# Function to insert a new node before the given node
def insertBeforeX(self, head, X, val):
if head is None:
return None
# Insert at the beginning if
# the value matches the head's data
if head.val == X:
return ListNode(val, head)
temp = head
while temp.next is not None:
# Insert at the current position if
# the next node has the desired value
if temp.next.val == X:
newNode = ListNode(val, temp.next)
temp.next = newNode
break
temp = temp.next
return head
# Helper Function to print the linked list
def printLL(head):
while head is not None:
print(head.val, end=" ")
head = head.next
print()
if __name__ == "__main__":
# Create a linked list from a list
arr = [1, 2, 4, 5]
X = 4
val = 3
head = ListNode(arr[0])
head.next = ListNode(arr[1])
head.next.next = ListNode(arr[2])
# Print the original list
print("Original List: ", end="")
printLL(head)
# Create a Solution object
sol = Solution()
head = sol.insertBeforeX(head, X, val)
# Print the modified linked list
print("List after inserting a new node before the given node: ", end="")
printLL(head)
// Definition of singly linked list
class ListNode {
constructor(val = 0, next = null) {
this.val = val;
this.next = next;
}
}
// Solution class
class Solution {
// Function to insert a new node before the given node
insertBeforeX(head, X, val) {
if (head === null) {
return null;
}
/* Insert at the beginning if the
value matches the head's data */
if (head.val === X) {
return new ListNode(val, head);
}
let temp = head;
while (temp.next !== null) {
/* Insert at the current position if the
next node has the desired value */
if (temp.next.val === X) {
let newNode = new ListNode(val, temp.next);
temp.next = newNode;
break;
}
temp = temp.next;
}
return head;
}
}
// Helper Function to print the linked list
function printLL(head) {
let current = head;
while (current !== null) {
process.stdout.write(current.val + " ");
current = current.next;
}
console.log();
}
// Main function
let arr = [1, 2, 4, 5];
let X = 4, val = 3;
let head = new ListNode(arr[0]);
head.next = new ListNode(arr[1]);
head.next.next = new ListNode(arr[2]);
// Print the original list
console.log("Original List: ");
printLL(head);
// Create a Solution object
let sol = new Solution();
head = sol.insertBeforeX(head, X, val);
// Print the modified linked list
console.log("List after inserting a new node before the given node: ");
printLL(head);
Q: How do you efficiently handle inserting before the head when X matches the head node's value?
A: When the first node has the value X, the new node should become the new head. Instead of handling this separately in the traversal logic, treat it as a special initialization case before the traversal begins.
Q: What happens when X is not found in the list?
A: In this case, the function should simply return the list unchanged. This ensures you’re not making invalid modifications or accidentally breaking the list structure.
Q: How would you handle a scenario where X is guaranteed to appear multiple times, and you want to insert only before the last occurrence of X?
A: This requires a two-pass traversal of the list. In the first pass, find the last occurrence of X. In the second pass, insert the new node before that occurrence.
Q: What optimizations can you apply if you frequently insert before a specific value like X?
A: Maintaining a hash map of value-to-node mappings can speed up the search process, reducing traversal time.