Stable Unique Column Renames
Reported by candidates from Microsoft's online assessment. Pattern, common pitfall, and the honest play if you blank under the timer.
Microsoft reported this one in September 2026, and the detail that trips people is right in the statement: "user.id" and "user_id" both normalize to the same base, and the order they show up decides who gets the suffix. It's a hash-table and simulation problem dressed up as a schema tool. You've got an OA coming and you want the trick, not a lecture. The trick is two maps and one careful rule about when names get assigned. If you blank on the live assessment, StealthCoder is the invisible safety net that reads the problem and hands you a working solution.
The problem
Process a sequence of table-schema snapshots. Each snapshot lists the currently visible raw column names in display order. The first time a raw name appears, replace every. with _. The assigned display name must be unique case-insensitively across every name ever assigned. If the normalized base is already used, append _1, _2, and so on using the smallest available suffix. A raw name keeps its assigned display name when it moves, disappears, or reappears in a later snapshot. Assigned names are never recycled. Return the renamed columns for every snapshot in the same shape and order. Function stableColumnNames(snapshots: String[][]) → String[][] Examples Example 1 snapshots = [["user.id","user_id"],["user_id","user.id"]] return = [["user_id","user_id_1"],["user_id_1","user_id"]] The colliding raw names keep their first assigned names after reordering. Example 2 snapshots = [["A"],["a"],["A"]] return = [["A"],["a_1"],["A"]] Uniqueness is case-insensitive while exact raw-name identity is persistent. Constraints 0 <= snapshots.length <= 10000. The total number of column occurrences is at most 200000. Raw names are nonempty and unique within one snapshot. Raw names contain letters, digits, underscores, and periods.
Reported by candidates. Source: FastPrep
Pattern and pitfall
Keep two structures. First, a map from raw name to its assigned display name, which makes the rename permanent. Second, a set of lowercase assigned names, which enforces case-insensitive uniqueness forever. Walk snapshots in order and columns in display order. If the raw name is already in the map, reuse it. If not, replace every period with an underscore, then check the lowercase form against the set. If it's taken, try _1, _2 and so on until one is free, then record it. The common pitfall is forgetting that suffixed names also go in the set, or that a later raw name can collide with an earlier generated suffix like user_id_1. Another trap is lowercasing the stored name, which breaks Example 2 where "A" must stay "A". Total work is linear in occurrences plus suffix probing. If you freeze on the live OA, StealthCoder is the hedge that gets you unstuck fast.
StealthCoder is the hedge for the one pattern you didn't drill. It runs invisibly during the screen share.
You can drill Stable Unique Column Renames cold, or you can hedge it. StealthCoder runs invisibly during screen share and surfaces a working solution in under 2 seconds. The proctor sees the IDE. They don't see what's behind it. If you're reading this with an OA window open, you're who this was built for.
Get StealthCoderRelated leaked OAs
You've seen the question.
Make sure you actually pass Microsoft's OA.
Microsoft reuses patterns across OAs. If you're reading this with an OA window open, you're who this was built for. Works on HackerRank, CodeSignal, CoderPad, and Karat.
Stable Unique Column Renames FAQ
What's the core trick in Stable Unique Column Renames?+
Persist two things: a raw-to-display map and a set of lowercase names ever assigned. The map gives stability across snapshots. The set gives case-insensitive uniqueness with no recycling. Assign only the first time a raw name appears, then reuse forever.
How hard is this Microsoft OA question really?+
Medium at most. There's no fancy algorithm. The difficulty is careful bookkeeping around collisions, case, and the smallest free suffix. If you handle those three, it's a short function. Most failures come from edge cases, not from the idea.
Why does Example 2 return a_1 for the lowercase a?+
Raw "A" was assigned "A" first. Raw "a" is a different raw name, but its lowercase form collides with "a" in the used set, so it gets the smallest free suffix, a_1. When "A" returns, it keeps "A" since raw identity is exact.
Can a generated suffix collide with a later raw name?+
Yes. If user_id gets user_id_1, a later raw name that normalizes to user_id_1 must be treated as taken too. That's why every assigned name, suffixed or not, goes into the lowercase set. Check the set each time you try a candidate.
How do I prepare for this in 48 hours?+
Write it once from scratch with a hash map and a hash set. Then test the two examples plus a case where a suffixed name collides with a later raw name, and an empty snapshots input. Don't memorize it. Know why each structure exists.