Imagine you're a delivery driver with a special power: you can teleport through at most k roads to make them cost zero! ๐โจ
You're given an undirected weighted graph with n nodes connected by edges. Each edge has a weight representing the travel cost. Your mission is to find the shortest path from source node s to destination node d, but here's the twist: you can make up to k edges have zero weight by "hopping" over them.
Goal: Find the minimum total cost to travel from s to d when you can eliminate the cost of at most k edges.
Input: Number of nodes n, array of edges [u, v, weight], source s, destination d, and maximum hops k.
Output: The minimum path cost with the given hop constraint.
Input & Output
example_1.py โ Basic Triangle Graph
$Input:n = 3, edges = [[0,1,5], [1,2,3], [0,2,8]], s = 0, d = 2, k = 1
โบOutput:3
๐ก Note:We have a triangle: 0--(5)--1--(3)--2 with direct edge 0--(8)--2. With k=1, we can make one edge free. Best strategy: take path 0โ1โ2, make edge 0โ1 free (cost 0), then pay 3 for edge 1โ2. Total cost = 3.
example_2.py โ No Hops Needed
$Input:n = 3, edges = [[0,1,1], [1,2,1], [0,2,3]], s = 0, d = 2, k = 2
โบOutput:2
๐ก Note:Direct path 0โ1โ2 costs only 2, which is better than the direct edge 0โ2 costing 3. Even though we have 2 hops available, we don't need to use any since the cheapest path is already optimal.
example_3.py โ Use All Hops
$Input:n = 4, edges = [[0,1,10], [1,2,10], [2,3,10], [0,3,25]], s = 0, d = 3, k = 2
โบOutput:10
๐ก Note:Path 0โ1โ2โ3 normally costs 30. With k=2 hops, we can make edges 0โ1 and 1โ2 free, leaving only edge 2โ3 costing 10. This beats the direct path 0โ3 costing 25.
The optimal approach uses a modified Dijkstra's algorithm with state tracking. Each state represents (node, hops_remaining), and we explore both paying for edges and using free hops. This transforms the problem into shortest path search in a 3D state space with time complexity O((V + E) * K * log(V * K)).
Common Approaches
Approach
Time
Space
Notes
โ
Brute Force (Try All Hop Combinations)
O(C(E,k) * (V + E) log V)
O(V + E)
Try every possible combination of k edges to make free, then find shortest path
Modified Dijkstra with State Tracking (Optimal)
O((V + E) * K * log(V * K))
O(V * K)
Use Dijkstra's algorithm with state (node, hops_used) to find optimal path
Brute Force (Try All Hop Combinations) โ Algorithm Steps
Generate all possible combinations of edges to make free (up to k edges)
For each combination, create a modified graph with selected edges having weight 0
Run Dijkstra's algorithm on each modified graph
Return the minimum path cost among all combinations
Visualization
Tap to expand
Step-by-Step Walkthrough
1
Generate Combinations
Generate all possible combinations of k edges to make free
2
Modify Graph
For each combination, create a graph with selected edges having weight 0
3
Run Dijkstra
Find shortest path in the modified graph
4
Track Minimum
Keep track of the minimum cost found across all combinations
Code -
solution.c โ C
#include <stdio.h>
#include <stdlib.h>
#include <limits.h>
#include <string.h>
typedef struct {
int to, weight;
} Edge;
typedef struct {
Edge* edges;
int count, capacity;
} AdjList;
typedef struct {
int cost, node;
} HeapNode;
typedef struct {
HeapNode* data;
int size, capacity;
} MinHeap;
MinHeap* createHeap(int capacity) {
MinHeap* heap = (MinHeap*)malloc(sizeof(MinHeap));
heap->data = (HeapNode*)malloc(capacity * sizeof(HeapNode));
heap->size = 0;
heap->capacity = capacity;
return heap;
}
void heapifyUp(MinHeap* heap, int idx) {
if (idx && heap->data[(idx-1)/2].cost > heap->data[idx].cost) {
HeapNode temp = heap->data[idx];
heap->data[idx] = heap->data[(idx-1)/2];
heap->data[(idx-1)/2] = temp;
heapifyUp(heap, (idx-1)/2);
}
}
void heapifyDown(MinHeap* heap, int idx) {
int smallest = idx;
int left = 2*idx + 1, right = 2*idx + 2;
if (left < heap->size && heap->data[left].cost < heap->data[smallest].cost)
smallest = left;
if (right < heap->size && heap->data[right].cost < heap->data[smallest].cost)
smallest = right;
if (smallest != idx) {
HeapNode temp = heap->data[idx];
heap->data[idx] = heap->data[smallest];
heap->data[smallest] = temp;
heapifyDown(heap, smallest);
}
}
void push(MinHeap* heap, int cost, int node) {
if (heap->size < heap->capacity) {
heap->data[heap->size].cost = cost;
heap->data[heap->size].node = node;
heapifyUp(heap, heap->size);
heap->size++;
}
}
HeapNode pop(MinHeap* heap) {
HeapNode root = heap->data[0];
heap->data[0] = heap->data[heap->size-1];
heap->size--;
heapifyDown(heap, 0);
return root;
}
int dijkstra(AdjList* graph, int start, int end, int n) {
int* dist = (int*)malloc(n * sizeof(int));
for (int i = 0; i < n; i++) dist[i] = INT_MAX;
dist[start] = 0;
MinHeap* pq = createHeap(n * n);
push(pq, 0, start);
while (pq->size > 0) {
HeapNode curr = pop(pq);
int cost = curr.cost, node = curr.node;
if (node == end) {
free(dist);
int result = cost;
free(pq->data);
free(pq);
return result;
}
if (cost > dist[node]) continue;
for (int i = 0; i < graph[node].count; i++) {
int neighbor = graph[node].edges[i].to;
int weight = graph[node].edges[i].weight;
int newCost = cost + weight;
if (newCost < dist[neighbor]) {
dist[neighbor] = newCost;
push(pq, newCost, neighbor);
}
}
}
int result = dist[end];
free(dist);
free(pq->data);
free(pq);
return result;
}
int shortestPathWithKHops(int n, int** edges, int edgesSize, int s, int d, int k) {
int minCost = INT_MAX;
// Simple implementation for small k - try all combinations
for (int mask = 0; mask < (1 << edgesSize) && __builtin_popcount(mask) <= k; mask++) {
if (__builtin_popcount(mask) > k) continue;
// Build graph with selected edges having weight 0
AdjList* graph = (AdjList*)calloc(n, sizeof(AdjList));
for (int i = 0; i < n; i++) {
graph[i].capacity = edgesSize * 2;
graph[i].edges = (Edge*)malloc(graph[i].capacity * sizeof(Edge));
}
for (int i = 0; i < edgesSize; i++) {
int u = edges[i][0], v = edges[i][1], w = edges[i][2];
int weight = (mask & (1 << i)) ? 0 : w;
graph[u].edges[graph[u].count++] = (Edge){v, weight};
graph[v].edges[graph[v].count++] = (Edge){u, weight};
}
int cost = dijkstra(graph, s, d, n);
if (cost < minCost) minCost = cost;
for (int i = 0; i < n; i++) free(graph[i].edges);
free(graph);
}
return minCost;
}
Time & Space Complexity
Time Complexity
โฑ๏ธ
O(C(E,k) * (V + E) log V)
C(E,k) combinations times Dijkstra's complexity for each
n
2n
โก Linearithmic
Space Complexity
O(V + E)
Space for graph representation and Dijkstra's data structures
n
2n
โ Linear Space
25.0K Views
MediumFrequency
~15 minAvg. Time
850 Likes
Ln 1, Col 1
Smart Actions
๐กExplanation
AI Ready
๐ก SuggestionTabto acceptEscto dismiss
// Output will appear here after running code
Code Editor Closed
Click the red button to reopen
Algorithm Visualization
Pinch to zoom โข Tap outside to close
Test Cases
0 passed
0 failed
3 pending
Select Compiler
Choose a programming language
Compiler list would appear here...
AI Editor Features
Header Buttons
๐ก
Explain
Get a detailed explanation of your code. Select specific code or analyze the entire file. Understand algorithms, logic flow, and complexity.
๐ง
Fix
Automatically detect and fix issues in your code. Finds bugs, syntax errors, and common mistakes. Shows you what was fixed.
๐ก
Suggest
Get improvement suggestions for your code. Best practices, performance tips, and code quality recommendations.
๐ฌ
Ask AI
Open an AI chat assistant to ask any coding questions. Have a conversation about your code, get help with debugging, or learn new concepts.
Smart Actions (Slash Commands)
๐ง
/fix Enter
Find and fix issues in your code. Detects common problems and applies automatic fixes.
๐ก
/explain Enter
Get a detailed explanation of what your code does, including time/space complexity analysis.
๐งช
/tests Enter
Automatically generate unit tests for your code. Creates comprehensive test cases.
๐
/docs Enter
Generate documentation for your code. Creates docstrings, JSDoc comments, and type hints.
โก
/optimize Enter
Get performance optimization suggestions. Improve speed and reduce memory usage.
AI Code Completion (Copilot-style)
๐ป
Ghost Text Suggestions
As you type, AI suggests code completions shown in gray text. Works with keywords like def, for, if, etc.
Tabto acceptEscto dismiss
๐ฌ
Comment-to-Code
Write a comment describing what you want, and AI generates the code. Try: # two sum, # binary search, # fibonacci
๐ก
Pro Tip: Select specific code before using Explain, Fix, or Smart Actions to analyze only that portion. Otherwise, the entire file will be analyzed.