Challenge - 5 Problems
Doubly Linked List Master
Get all challenges correct to earn this badge!
Test your skills under time pressure!
❓ Predict Output
intermediate2:00remaining
Output after inserting nodes at the end
What is the printed state of the doubly linked list after inserting 10, 20, and 30 at the end?
DSA C
typedef struct Node {
int data;
struct Node* prev;
struct Node* next;
} Node;
#include <stdio.h>
#include <stdlib.h>
Node* insertAtEnd(Node* head, int data) {
Node* newNode = (Node*)malloc(sizeof(Node));
newNode->data = data;
newNode->next = NULL;
if (head == NULL) {
newNode->prev = NULL;
return newNode;
}
Node* temp = head;
while (temp->next != NULL) {
temp = temp->next;
}
temp->next = newNode;
newNode->prev = temp;
return head;
}
void printList(Node* head) {
Node* temp = head;
while (temp != NULL) {
printf("%d -> ", temp->data);
temp = temp->next;
}
printf("null\n");
}
int main() {
Node* head = NULL;
head = insertAtEnd(head, 10);
head = insertAtEnd(head, 20);
head = insertAtEnd(head, 30);
printList(head);
return 0;
}Attempts:
2 left
💡 Hint
Remember that inserting at the end adds the new node after the last node.
✗ Incorrect
The insertAtEnd function adds nodes at the end, so the list grows as 10, then 10->20, then 10->20->30. The printList function prints nodes from head to tail.
❓ Predict Output
intermediate2:00remaining
Output after inserting into an empty list
What is the printed state of the doubly linked list after inserting a single node with value 5 into an empty list?
DSA C
typedef struct Node {
int data;
struct Node* prev;
struct Node* next;
} Node;
#include <stdio.h>
#include <stdlib.h>
Node* insertAtEnd(Node* head, int data) {
Node* newNode = (Node*)malloc(sizeof(Node));
newNode->data = data;
newNode->next = NULL;
if (head == NULL) {
newNode->prev = NULL;
return newNode;
}
Node* temp = head;
while (temp->next != NULL) {
temp = temp->next;
}
temp->next = newNode;
newNode->prev = temp;
return head;
}
void printList(Node* head) {
Node* temp = head;
while (temp != NULL) {
printf("%d -> ", temp->data);
temp = temp->next;
}
printf("null\n");
}
int main() {
Node* head = NULL;
head = insertAtEnd(head, 5);
printList(head);
return 0;
}Attempts:
2 left
💡 Hint
Inserting into an empty list creates a single node which is both head and tail.
✗ Incorrect
Since the list is empty, the new node becomes the head with no previous or next nodes. The print shows the single node followed by null.
🔧 Debug
advanced2:00remaining
Identify the bug causing a segmentation fault
Why does the following insertAtEnd function cause a segmentation fault when inserting into a non-empty list?
DSA C
Node* insertAtEnd(Node* head, int data) { Node* newNode = (Node*)malloc(sizeof(Node)); newNode->data = data; newNode->next = NULL; if (head == NULL) { newNode->prev = NULL; return newNode; } Node* temp = head; while (temp->next != NULL) { temp = temp->next; } temp->next = newNode; // Missing assignment here return head; }
Attempts:
2 left
💡 Hint
Check if all pointers of the new node are properly assigned.
✗ Incorrect
The function forgets to set newNode->prev = temp. Without this, the prev pointer is uninitialized and can cause a segmentation fault when accessed.
❓ Predict Output
advanced2:30remaining
Output after multiple insertions and one deletion
Given the code below, what is the printed list after inserting 1, 2, 3 at the end and then deleting the node with value 2?
DSA C
typedef struct Node {
int data;
struct Node* prev;
struct Node* next;
} Node;
#include <stdio.h>
#include <stdlib.h>
Node* insertAtEnd(Node* head, int data) {
Node* newNode = (Node*)malloc(sizeof(Node));
newNode->data = data;
newNode->next = NULL;
if (head == NULL) {
newNode->prev = NULL;
return newNode;
}
Node* temp = head;
while (temp->next != NULL) {
temp = temp->next;
}
temp->next = newNode;
newNode->prev = temp;
return head;
}
Node* deleteNode(Node* head, int key) {
Node* temp = head;
while (temp != NULL && temp->data != key) {
temp = temp->next;
}
if (temp == NULL) return head;
if (temp->prev != NULL) temp->prev->next = temp->next;
else head = temp->next;
if (temp->next != NULL) temp->next->prev = temp->prev;
free(temp);
return head;
}
void printList(Node* head) {
Node* temp = head;
while (temp != NULL) {
printf("%d -> ", temp->data);
temp = temp->next;
}
printf("null\n");
}
int main() {
Node* head = NULL;
head = insertAtEnd(head, 1);
head = insertAtEnd(head, 2);
head = insertAtEnd(head, 3);
head = deleteNode(head, 2);
printList(head);
return 0;
}Attempts:
2 left
💡 Hint
Deleting node with value 2 removes it from the list, linking 1 directly to 3.
✗ Incorrect
The deleteNode function removes the node with data 2 and correctly updates the previous and next pointers, resulting in the list 1 -> 3 -> null.
🧠 Conceptual
expert1:30remaining
Why is updating the prev pointer important in doubly linked list insertion?
In the insertAtEnd function for a doubly linked list, why must we update the new node's prev pointer to point to the last node?
Attempts:
2 left
💡 Hint
Think about how doubly linked lists allow moving backwards.
✗ Incorrect
The prev pointer allows moving backward through the list. Without setting it, backward traversal breaks, causing incorrect behavior.
