Code Logo

Harbor Ferry Route Planner

Published at05 Jan 2026
2D Array Easy 36 views
Like25

Think of a small harbor challenge where order and timing really matter. In Harbor Ferry Route Planner, you are trying to work toward the right number by following one clear idea.

This problem feels a bit like a maze or map challenge. You need to think about how moves, paths, or links work together. Some places may still connect nicely, while others may be blocked or no longer fit the rule. The answer comes from following those connections carefully.

For example, if the input is n = 4, routes = [[0,1],[1,2],[2,3]], origin = 3, max_transfers = 0, the answer is 1. With no transfers allowed, only the starting dock receives the announcement. Another example is n = 5, routes = [[0,1],[1,2],[2,0],[3,4]], origin = 1, max_transfers = 1, which gives 3. Docks 0, 1, and 2 form a reachable group within one transfer of the origin.

This is a friendly practice problem, but it still rewards careful reading. The key is keeping track of where you can move and which routes still follow the rule.

Example Input & Output

Example 1
Input
n = 4, routes = [[0,1],[1,2],[2,3]], origin = 3, max_transfers = 0
Output
1
Explanation

With no transfers allowed, only the starting dock receives the announcement.

Example 2
Input
n = 5, routes = [[0,1],[1,2],[2,0],[3,4]], origin = 1, max_transfers = 1
Output
3
Explanation

Docks 0, 1, and 2 form a reachable group within one transfer of the origin.

Example 3
Input
n = 6, routes = [[0,1],[1,2],[2,3],[3,4],[4,5]], origin = 0, max_transfers = 3
Output
4
Explanation

The crew may visit docks 0, 1, 2, and 3 before exceeding the transfer cap.

Algorithm Flow

Recommendation Algorithm Flow for Harbor Ferry Route Planner

Solution Approach

This problem is best solved with a breadth-first search (BFS) over the dock graph. The goal is to count how many docks can be reached from the origin within a limited number of transfers, treating each transfer as one edge move in the graph.

BFS is the right tool here because it explores nodes in order of their distance from the start. Since every edge counts as exactly one transfer, BFS guarantees we stop exactly at the allowed depth and never need to process deeper nodes.

We start by building an undirected adjacency list from the routes, then run BFS from the origin:

function ferry_route_reach(n, routes, origin, max_transfers) {
    const graph = {};
    for (let i = 0; i < n; i++) graph[i] = [];
    for (const [u, v] of routes) {
        graph[u].push(v);
        graph[v].push(u);
    }

    const visited = new Set([origin]);
    const queue = [[origin, 0]];

    while (queue.length > 0) {
        const [harbor, transfers] = queue.shift();
        if (transfers < max_transfers) {
            for (const neighbor of graph[harbor]) {
                if (!visited.has(neighbor)) {
                    visited.add(neighbor);
                    queue.push([neighbor, transfers + 1]);
                }
            }
        }
    }

    return visited.size;
}

First we build the graph. Because routes are undirected, each pair [u, v] adds v to u's neighbors and u to v's neighbors. We initialize every dock with an empty list so that docks with no connections are still represented.

We then seed the queue with the origin at transfer level 0 and mark it visited. In the loop, we only expand a dock if its transfer count is still below max_transfers. Each unvisited neighbor is marked and pushed with transfers + 1, so the distance grows correctly as we go deeper.

Let us trace the example n = 5, routes = [[0,1],[1,2],[2,0],[3,4]], origin = 1, max_transfers = 1. Starting at dock 1, we can reach 0 and 2 in one transfer. Dock 3 and 4 are in a separate component, so they stay unreachable. The visited set contains docks {1, 0, 2}, giving a count of 3.

When max_transfers = 0, the loop never expands the origin, so only the origin is counted — matching the expected answer of 1 in that case.

The time complexity is O(n + e), where e is the number of routes, and the space complexity is O(n) for the graph and visited set.

Best Answers

java
import java.util.*;
class Solution {
    public int ferry_route_reach(int n, int[][] routes, int origin, int max_transfers) {
        Map<Integer, List<Integer>> graph = new HashMap<>();
        for (int i = 0; i < n; i++) graph.put(i, new ArrayList<>());
        for (int[] route : routes) {
            graph.get(route[0]).add(route[1]);
            graph.get(route[1]).add(route[0]);
        }
        
        Set<Integer> visited = new HashSet<>();
        visited.add(origin);
        Queue<int[]> queue = new LinkedList<>();
        queue.offer(new int[]{origin, 0});
        
        while (!queue.isEmpty()) {
            int[] curr = queue.poll();
            int harbor = curr[0], transfers = curr[1];
            if (transfers < max_transfers) {
                for (int neighbor : graph.get(harbor)) {
                    if (!visited.contains(neighbor)) {
                        visited.add(neighbor);
                        queue.offer(new int[]{neighbor, transfers + 1});
                    }
                }
            }
        }
        
        return visited.size();
    }
}