Solve three algorithmic OA problems
DRWSoftware Engineer · Online AssessmentLast updated
This set evaluates algorithmic problem-solving skills including array manipulation and simulation for knockout tournament dynamics, graph traversal and constructive movement-sequence design on grids, and broader competencies in handling permutations, connectivity, and constraint-driven constructions.
This is an online assessment (Codility-style, 150 minutes) consisting of three independent coding problems. Solve each one separately; they do not share input or state.
Part 1 — Knockout Tournament Match Counts
There are $n$ players standing in a line, indexed $1$ to $n$. Player $i$ has a distinct skill value $a[i]$, and the values $a[1..n]$ form a permutation of the integers $1$ to $n$ (so all skills are distinct).
A series of knockout rounds is played:
- In each round, the surviving players are paired from left to right: positions $1$ vs $2$, $3$ vs $4$, and so on.
- In each pair, the player with the higher skill value wins and advances; the other is eliminated and leaves the tournament.
- After a round, the winners keep their relative left-to-right order and form the player sequence for the next round.
- Rounds continue until exactly one player (the overall champion) remains.
Define $b[1..n]$ where $b[i]$ is the total number of matches the original player $i$ participates in (until they are eliminated, or until they win the tournament).
Task: Given $n$ and the skill array $a[1..n]$, return the array $b[1..n]$.
What This Part Should Cover
- Recognizing that match count equals the number of rounds the player remains alive (one match per round per alive player).
- A correct round-by-round simulation (or equivalent divide-and-conquer / segment recursion) that preserves left-to-right winner ordering.
- Complexity argument: total work across all rounds is $\sum_k n/2^k = O(n)$ comparisons plus $O(n \log n)$ for the increments — comfortably within $n \le 200{,}000$.
- Correct handling of the champion (they play $k = \log_2 n$ matches, the maximum).
Part 2 — Robot Path Planning with Movement Instructions
You are given an $R \times C$ grid ($3 \le R, C \le 50$). Each cell is one of:
#— wall (cannot be entered),.— empty floor (can be entered),*— the robot's starting cell (also a traversable floor cell).
Guarantees: the outer border (first/last row, first/last column) is entirely walls; all floor cells form a single connected component; the robot starts on a floor cell.
You control the robot with characters ^ (up), v (down), < (left), > (right). Every move must keep the robot inside the grid and on a floor cell (. or *). You do not need to return to the start.
Construct an instruction string for each of the five variants below. For every variant the output length must be at most $100{,}000$. Any valid sequence is accepted — shortest-path optimality is not required. Assume each described shape admits such a sequence within the bound.
The variants:
-
Subtask 1 — Rectangular border walk. All floor cells form a solid axis-aligned rectangle. The start is at the rectangle's top-left corner. Visit exactly the border (perimeter) cells, all of them, and never step on an interior floor cell.
-
Subtask 2 — Full rectangular coverage. Floor cells form a solid rectangle; start anywhere inside; visit every floor cell at least once.
-
Subtask 3 — Dumbbell. Two disjoint rectangles connected by a single floor cell (a 1-cell corridor); start anywhere; visit every floor cell.
-
Subtask 4 — Simple path. The floor cells form a simple path in the orthogonal-adjacency graph (no branches, no cycles); start anywhere on it; visit every cell.
-
Subtask 5 — Arbitrary connected shape. Any connected floor region (per the global guarantees); start anywhere; visit every floor cell.
Task (all subtasks): Output one valid instruction string of ^v<> that keeps the robot on floor cells and meets the variant's visitation requirement, with length $\le 100{,}000$. You may treat each subtask as its own test case with its own grid.
What This Part Should Cover
- A single coverage routine (DFS Euler tour with inverse-move backtracking) handling subtasks 2–5 uniformly, plus the realization that subtask 1 needs its own perimeter walk because interior cells are forbidden.
- A correct, explicit length argument tying $2(V-1)$ to the $100{,}000$ bound.
- Move/inverse-move bookkeeping and a
visitedset so the robot never re-enters as a "new" cell and never steps onto a wall or out of bounds. - Handling degenerate shapes (single floor cell ⇒ empty string; a 1-wide rectangle in subtask 1 where the "perimeter" is the whole region).
Part 3 — Maximum Sum of Two Numbers Without Shared Digits
You are given an array of $n$ integers $a[1..n]$ ($1 \le n \le 200{,}000$). Assume each $a[i]$ is a non-negative integer (state a reasonable upper bound, e.g. up to $10^9$, if your method needs one).
Two numbers have no common digit if, written in base-10 without leading zeros, their digit sets are disjoint. For example $12$ and $340$ are allowed; $15$ and $51$ are not (they share 1 and 5).
Task: Choose two distinct indices $i\ne j$ such that $a[i]$ and $a[j]$ share no digit and $a[i] + a[j]$ is maximized. Output that maximum sum. If no valid pair exists, return a sentinel value (e.g. $-1$) and document it.
What This Part Should Cover
- The 10-bit digit-mask reduction and keeping only the max value per mask ($\le 1024$ survivors) — turning a quadratic-in-$n$ search into one over a constant 1024-mask space.
- A correct disjointness test (
mask1 & mask2 == 0) and a correct argument that the distinct-index constraint is satisfied automatically. - Either the $O(1024^2)$ mask-pair scan or the $O(10 \cdot 2^{10})$ SOS/complement approach, with overall complexity $O(n \log(\max a) + 2^{10} \cdot 10)$.
- Defined, documented behavior when no compatible pair exists.
Hints
Hint 1
Reframe the structure: Because $n = 2^k$, the bracket is a perfect binary tree of depth $k$. A player who survives to round $r$ (1-indexed) has played exactly $r$ matches; they get one more match each round until they lose.
Hint 2
A clean way to count: You do not need to know *who* wins each round to count matches — every still-alive player plays exactly one match per round. So $b[i] = (\text{number of rounds player } i \text{ survives into})$. Simulate round by round: increment $b$ for every alive player, then keep the per-pair winner. This is $O(n \log n)$ total work, since the alive set halves each round.
Hint 3
One algorithm covers most of it: Variants 2–5 all ask for *full coverage* of an arbitrary (or special-case) connected region. A single technique solves all of them: a DFS over the floor cells, emitting the move character when you step into a new cell and the inverse move (`^`↔`v`, `<`↔`>`) when you backtrack. This produces an Euler tour of a spanning tree.
Hint 4
Why the length bound is safe: A DFS-backtracking walk traverses each spanning-tree edge exactly twice, so its length is $2 \cdot (V-1)$ where $V$ is the number of floor cells. With border walls, $V \le 48 \times 48 = 2304$, giving at most $\approx 4606$ moves — far under $100{,}000$. Subtask 1 (border-only walk) is the one case the generic DFS does *not* solve, since it forbids interior cells; handle it separately by walking the rectangle's perimeter explicitly.
Hint 5
Compress each number to a 10-bit signature: Each number's relevant information is just *which of the digits 0–9 it contains* — a 10-bit mask. There are only $2^{10} = 1024$ possible masks. Reduce the array to: for each mask, the **maximum** value having exactly that digit set.
Hint 6
Pair masks by disjointness: Two numbers are compatible iff their masks AND to $0$. Naively pair all surviving masks ($\le 1024^2 \approx 10^6$ pairs) and take the best disjoint pair — or, faster, use a Sum-Over-Subsets (SOS) DP so that for each mask $m$ you instantly look up the best value whose mask is a subset of the complement $\lnot m$. Note no number has an empty mask (even `0` contains digit `0`), so a number is never disjoint with itself — the $i \ne j$ requirement is automatic across distinct masks.
Follow-up questions
- **Part 1:** Instead of $b[i]$, return for each player the skill value of the opponent who eliminated them (and a sentinel for the champion). How does your simulation change?
- **Part 2:** For subtask 5, can you guarantee a covering walk of length **strictly less** than $2(V-1)$ in general, or is that bound tight? What grid shape forces it to be tight?
- **Part 3:** Generalize to selecting $k$ numbers (not just two) that are pairwise digit-disjoint with maximum total sum. How does the mask-DP change, and what is the complexity?
- **Part 3:** If the "no common digit" rule were replaced by "share at most one common digit," how would you adapt the mask approach?
Solution walkthrough is for members
Get the full walkthrough with reference code and complexity analysis, plus Kitty Coach at 300 messages a day. Hints, the code runner and community answers stay free.