Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
Original file line number Diff line number Diff line change
Expand Up @@ -25,13 +25,13 @@ echo "Gateway IP: $GATEWAY_IP"
if [ -z "$RESOURCE_GROUP" ]; then
echo "Finding resource group for DNS zone $DNS_ZONE..."
RESOURCE_GROUP=$(az network dns zone list --query "[?name=='$DNS_ZONE'].resourceGroup | [0]" -o tsv)

if [ -z "$RESOURCE_GROUP" ]; then
echo "ERROR: Could not find resource group for DNS zone $DNS_ZONE"
echo "Please set RESOURCE_GROUP environment variable or create the DNS zone first."
exit 1
fi

echo "Found resource group: $RESOURCE_GROUP"
fi

Expand Down
52 changes: 48 additions & 4 deletions src/interview_workbook/leetcode/backtracking/combination_sum.py
Original file line number Diff line number Diff line change
Expand Up @@ -12,6 +12,10 @@

from typing import List

from src.interview_workbook.leetcode._registry import register_problem
from src.interview_workbook.leetcode._runner import TestCase
from src.interview_workbook.leetcode._types import Category, Difficulty


class Solution:
def combinationSum(self, candidates: List[int], target: int) -> List[List[int]]:
Expand All @@ -29,11 +33,51 @@ def backtrack(start: int, path: List[int], total: int):
path.pop()

backtrack(0, [], 0)
print(f"All combinations: {res}")
return res


# Example test cases
test_cases = [
TestCase(([2, 3, 6, 7], 7), [[2, 2, 3], [7]], "Standard case"),
TestCase(([2, 3, 5], 8), [[2, 2, 2, 2], [2, 3, 3], [3, 5]], "Multiple solutions"),
TestCase(([2], 1), [], "No solution possible"),
]


def demo() -> str:
s = Solution()
result = s.combinationSum([2, 3, 6, 7], 7)
return str(result)
"""Run test cases for Combination Sum."""
sol = Solution()
outputs = []
outputs.append("Combination Sum | LeetCode 39")
outputs.append("=" * 50)
outputs.append("Time: O(2^target/min) | Space: O(target/min)")
outputs.append("Technique: Backtracking with pruning\n")

for case in test_cases:
res = sol.combinationSum(*case.input_args)
# Sort for comparison since order may vary
res_sorted = sorted([sorted(x) for x in res])
expected_sorted = sorted([sorted(x) for x in case.expected])
passed = res_sorted == expected_sorted
status = "✓ PASS" if passed else "✗ FAIL"
outputs.append(f"Test Case: {case.description}")
outputs.append(f" Input: candidates={case.input_args[0]}, target={case.input_args[1]}")
outputs.append(f" Output: {res}")
outputs.append(f" Expected: {case.expected}")
outputs.append(f" {status}\n")

result = "\n".join(outputs)
print(result)
return result


register_problem(
id=39,
slug="combination_sum",
title="Combination Sum",
category=Category.BACKTRACKING,
difficulty=Difficulty.MEDIUM,
tags=["array", "backtracking"],
url="https://leetcode.com/problems/combination-sum/",
notes="",
)
43 changes: 38 additions & 5 deletions src/interview_workbook/leetcode/backtracking/combination_sum_ii.py
Original file line number Diff line number Diff line change
Expand Up @@ -11,6 +11,7 @@
from typing import List

from src.interview_workbook.leetcode._registry import register_problem
from src.interview_workbook.leetcode._runner import TestCase
from src.interview_workbook.leetcode._types import Category, Difficulty


Expand All @@ -36,11 +37,43 @@ def backtrack(start, path, remain):
return res


def demo():
s = Solution()
result = s.combinationSum2([10, 1, 2, 7, 6, 1, 5], 8)
print(f"Final result: {result}")
return str(result)
# Example test cases
test_cases = [
TestCase(
([10, 1, 2, 7, 6, 1, 5], 8),
[[1, 1, 6], [1, 2, 5], [1, 7], [2, 6]],
"Standard case with duplicates",
),
TestCase(([2, 5, 2, 1, 2], 5), [[1, 2, 2], [5]], "Multiple ways to reach target"),
TestCase(([1, 1, 1, 1], 2), [[1, 1]], "All same elements"),
]


def demo() -> str:
"""Run test cases for Combination Sum II."""
sol = Solution()
outputs = []
outputs.append("Combination Sum II | LeetCode 40")
outputs.append("=" * 50)
outputs.append("Time: O(2^n) | Space: O(n)")
outputs.append("Technique: Backtracking with duplicate skipping\n")

for case in test_cases:
res = sol.combinationSum2(*case.input_args)
# Sort for comparison since order may vary
res_sorted = sorted([sorted(x) for x in res])
expected_sorted = sorted([sorted(x) for x in case.expected])
passed = res_sorted == expected_sorted
status = "✓ PASS" if passed else "✗ FAIL"
outputs.append(f"Test Case: {case.description}")
outputs.append(f" Input: candidates={case.input_args[0]}, target={case.input_args[1]}")
outputs.append(f" Output: {res}")
outputs.append(f" Expected: {case.expected}")
outputs.append(f" {status}\n")

result = "\n".join(outputs)
print(result)
return result


register_problem(
Expand Down
43 changes: 38 additions & 5 deletions src/interview_workbook/leetcode/backtracking/permutations.py
Original file line number Diff line number Diff line change
Expand Up @@ -7,6 +7,7 @@
from typing import List

from src.interview_workbook.leetcode._registry import register_problem
from src.interview_workbook.leetcode._runner import TestCase
from src.interview_workbook.leetcode._types import Category, Difficulty


Expand All @@ -27,11 +28,43 @@ def backtrack(start=0):
return res


def demo():
s = Solution()
result = s.permute([1, 2, 3])
print(f"Final result: {result}")
return str(result)
# Example test cases
test_cases = [
TestCase(
([1, 2, 3],),
[[1, 2, 3], [1, 3, 2], [2, 1, 3], [2, 3, 1], [3, 1, 2], [3, 2, 1]],
"Three elements",
),
TestCase(([0, 1],), [[0, 1], [1, 0]], "Two elements"),
TestCase(([1],), [[1]], "Single element"),
]


def demo() -> str:
"""Run test cases for Permutations."""
sol = Solution()
outputs = []
outputs.append("Permutations | LeetCode 46")
outputs.append("=" * 50)
outputs.append("Time: O(n! * n) | Space: O(n)")
outputs.append("Technique: Backtracking with in-place swapping\n")

for case in test_cases:
res = sol.permute(list(case.input_args[0])) # Copy to avoid mutation
# Sort for comparison since order may vary
res_sorted = sorted([tuple(x) for x in res])
expected_sorted = sorted([tuple(x) for x in case.expected])
passed = res_sorted == expected_sorted
status = "✓ PASS" if passed else "✗ FAIL"
outputs.append(f"Test Case: {case.description}")
outputs.append(f" Input: nums={list(case.input_args[0])}")
outputs.append(f" Output: {res}")
outputs.append(f" Expected: {case.expected}")
outputs.append(f" {status}\n")

result = "\n".join(outputs)
print(result)
return result


register_problem(
Expand Down
44 changes: 37 additions & 7 deletions src/interview_workbook/leetcode/backtracking/subsets.py
Original file line number Diff line number Diff line change
Expand Up @@ -9,6 +9,7 @@
from typing import List

from src.interview_workbook.leetcode._registry import register_problem
from src.interview_workbook.leetcode._runner import TestCase
from src.interview_workbook.leetcode._types import Category, Difficulty


Expand All @@ -20,20 +21,49 @@ def backtrack(start: int, path: List[int]) -> None:
res.append(path[:])
for i in range(start, len(nums)):
path.append(nums[i])
print(f"Path after append: {path}")
backtrack(i + 1, path)
path.pop()

backtrack(0, [])
print(f"All subsets: {res}")
return res


def demo():
s = Solution()
result = s.subsets([1, 2, 3])
print(f"Final result: {result}")
return str(result)
# Example test cases
test_cases = [
TestCase(
([1, 2, 3],),
[[], [1], [1, 2], [1, 2, 3], [1, 3], [2], [2, 3], [3]],
"Three elements",
),
TestCase(([0],), [[], [0]], "Single element"),
]


def demo() -> str:
"""Run test cases for Subsets."""
sol = Solution()
outputs = []
outputs.append("Subsets | LeetCode 78")
outputs.append("=" * 50)
outputs.append("Time: O(n * 2^n) | Space: O(n)")
outputs.append("Technique: Backtracking to generate power set\n")

for case in test_cases:
res = sol.subsets(list(case.input_args[0]))
# Sort for comparison since order may vary
res_sorted = sorted([tuple(sorted(x)) for x in res])
expected_sorted = sorted([tuple(sorted(x)) for x in case.expected])
passed = res_sorted == expected_sorted
status = "✓ PASS" if passed else "✗ FAIL"
outputs.append(f"Test Case: {case.description}")
outputs.append(f" Input: nums={list(case.input_args[0])}")
outputs.append(f" Output: {res}")
outputs.append(f" Expected: {case.expected}")
outputs.append(f" {status}\n")

result = "\n".join(outputs)
print(result)
return result


register_problem(
Expand Down
56 changes: 52 additions & 4 deletions src/interview_workbook/leetcode/backtracking/subsets_ii.py
Original file line number Diff line number Diff line change
Expand Up @@ -8,6 +8,7 @@
from typing import List

from src.interview_workbook.leetcode._registry import register_problem
from src.interview_workbook.leetcode._runner import TestCase
from src.interview_workbook.leetcode._types import Category, Difficulty


Expand All @@ -29,11 +30,58 @@ def backtrack(start: int, path: List[int]) -> None:
return res


# Example test cases
test_cases = [
TestCase(
([1, 2, 2],),
[[], [1], [1, 2], [1, 2, 2], [2], [2, 2]],
"Array with duplicates",
),
TestCase(([0],), [[], [0]], "Single element"),
TestCase(
([4, 4, 4, 1, 4],),
[
[],
[1],
[1, 4],
[1, 4, 4],
[1, 4, 4, 4],
[1, 4, 4, 4, 4],
[4],
[4, 4],
[4, 4, 4],
[4, 4, 4, 4],
],
"Multiple duplicates",
),
]


def demo() -> str:
s = Solution()
result = s.subsetsWithDup([1, 2, 2])
print(f"Final result: {result}")
return str(result)
"""Run test cases for Subsets II."""
sol = Solution()
outputs = []
outputs.append("Subsets II | LeetCode 90")
outputs.append("=" * 50)
outputs.append("Time: O(n * 2^n) | Space: O(n)")
outputs.append("Technique: Backtracking with duplicate skipping\n")

for case in test_cases:
res = sol.subsetsWithDup(list(case.input_args[0]))
# Sort for comparison since order may vary
res_sorted = sorted([tuple(sorted(x)) for x in res])
expected_sorted = sorted([tuple(sorted(x)) for x in case.expected])
passed = res_sorted == expected_sorted
status = "✓ PASS" if passed else "✗ FAIL"
outputs.append(f"Test Case: {case.description}")
outputs.append(f" Input: nums={list(case.input_args[0])}")
outputs.append(f" Output: {res}")
outputs.append(f" Expected: {case.expected}")
outputs.append(f" {status}\n")

result = "\n".join(outputs)
print(result)
return result


register_problem(
Expand Down
45 changes: 37 additions & 8 deletions src/interview_workbook/leetcode/binary_search/binary_search.py
Original file line number Diff line number Diff line change
@@ -1,10 +1,13 @@
"""
Binary Search

TODO: Add problem description
Problem: Binary Search
LeetCode link: https://leetcode.com/problems/binary-search/
Description: Given a sorted array and a target, return the index of target if found, else -1.
"""

from src.interview_workbook.leetcode._registry import register_problem
from src.interview_workbook.leetcode._runner import TestCase


class Solution:
Expand All @@ -22,13 +25,39 @@ def search(self, nums: list[int], target: int) -> int:
return -1


def demo():
"""Run a demo for the Binary Search problem."""
solver = Solution()
nums = [-1, 0, 3, 5, 9, 12]
target = 9
result = solver.search(nums, target)
return str(result)
# Example test cases
test_cases = [
TestCase(([-1, 0, 3, 5, 9, 12], 9), 4, "Target in middle"),
TestCase(([-1, 0, 3, 5, 9, 12], 2), -1, "Target not found"),
TestCase(([5], 5), 0, "Single element found"),
TestCase(([2, 5], 2), 0, "Target at start"),
TestCase(([2, 5], 5), 1, "Target at end"),
]


def demo() -> str:
"""Run test cases for Binary Search."""
sol = Solution()
outputs = []
outputs.append("Binary Search | LeetCode 704")
outputs.append("=" * 50)
outputs.append("Time: O(log n) | Space: O(1)")
outputs.append("Technique: Classic binary search\n")

for case in test_cases:
nums, target = case.input_args
res = sol.search(list(nums), target)
passed = res == case.expected
status = "✓ PASS" if passed else "✗ FAIL"
outputs.append(f"Test Case: {case.description}")
outputs.append(f" Input: nums={list(nums)}, target={target}")
outputs.append(f" Output: {res}")
outputs.append(f" Expected: {case.expected}")
outputs.append(f" {status}\n")

result = "\n".join(outputs)
print(result)
return result


# Register the problem with correct parameters
Expand Down
Loading
Loading