Keep Stable Unique Column Names Across Schema Changes

Read the full interview experience this question came from →

Quick Overview

Maintain stable case-insensitive unique column names across additions, removals, reordering, reappearance, and natural suffix collisions, with independent table histories.

Keep Stable Unique Column Names Across Schema Changes

Company: Microsoft

Role: Software Engineer

Category: Coding & Algorithms

Difficulty: medium

Interview Round: Onsite

Return stable effective column names for repeated snapshots of table schemas. Replace every dot in an original column name with an underscore. Effective names must be unique within a table, ignoring ASCII case. Resolve collisions with suffixes `_1`, `_2`, and so on. Implement `rename_columns(calls: string[][]) -> string[][]`. Each input row is `[tableName, column1, column2, ...]` and describes that table's current ordered column list. Return one array of effective column names per call, in the same order as its columns. ### Constraints & Assumptions - At most 1000 calls and 10000 column occurrences in total. Names contain ASCII letters, digits, dots, and underscores and are nonempty; each name is at most 100 characters. - Table identity and original column identity use exact case-sensitive strings. No original column is repeated within a single call. Different original names differing only in case remain different columns and need distinct effective names. - Each table maintains an independent persistent mapping for all original names ever seen during this function call. Once assigned, an effective name never changes, even if the column disappears, moves, or later returns. - Effective names assigned to absent columns remain reserved. This reservation policy makes the reported reappearance guarantee explicit. - Process newly encountered columns in their input order. The initial candidate is the original name with dots replaced by underscores. If its case-insensitive form is reserved, try that entire candidate plus `_1`, then `_2`, and so on, choosing the first unused suffix. Preserve the candidate's original case in the assigned name. - Natural suffixes are ordinary name text. For example, a new original `a_1` whose candidate is already reserved may become `a_1_1`, not automatically `a_2`. - Calls and returned arrays may contain zero columns. ### Example ```text calls = [["T","a.b","a_b","a_b_1"], ["T","a_b"], ["T","a_b_1","a.b","A.B"], ["U","a_b"]] result = [["a_b","a_b_1","a_b_1_1"], ["a_b_1"], ["a_b_1_1","a_b","A_B_2"], ["a_b"]] ``` Explain why rebuilding names from only the current snapshot breaks stability, and how you handle a natural suffixed name colliding with an earlier generated name. Analyze repeated collision searches rather than assuming every new assignment is constant time. ```hint Keep identity and reservation separate The original-to-effective mapping preserves historical identity. A second case-normalized set answers whether a candidate effective name is already reserved for that table. ```

Overview: Maintain stable case-insensitive unique column names across additions, removals, reordering, reappearance, and natural suffix collisions, with independent table histories.

Read the full Microsoft Software Engineer interview experience this question came from

|Home/Coding & Algorithms/Microsoft
Microsoft logo
Microsoft
Aug 30, 2026
mediumSoftware EngineerOnsiteCoding & Algorithms
0
0

Return stable effective column names for repeated snapshots of table schemas. Replace every dot in an original column name with an underscore. Effective names must be unique within a table, ignoring ASCII case. Resolve collisions with suffixes _1, _2, and so on.

Implement rename_columns(calls: string[][]) -> string[][]. Each input row is [tableName, column1, column2, ...] and describes that table's current ordered column list. Return one array of effective column names per call, in the same order as its columns.

Constraints & Assumptions

  • At most 1000 calls and 10000 column occurrences in total. Names contain ASCII letters, digits, dots, and underscores and are nonempty; each name is at most 100 characters.
  • Table identity and original column identity use exact case-sensitive strings. No original column is repeated within a single call. Different original names differing only in case remain different columns and need distinct effective names.
  • Each table maintains an independent persistent mapping for all original names ever seen during this function call. Once assigned, an effective name never changes, even if the column disappears, moves, or later returns.
  • Effective names assigned to absent columns remain reserved. This reservation policy makes the reported reappearance guarantee explicit.
  • Process newly encountered columns in their input order. The initial candidate is the original name with dots replaced by underscores. If its case-insensitive form is reserved, try that entire candidate plus _1 , then _2 , and so on, choosing the first unused suffix. Preserve the candidate's original case in the assigned name.
  • Natural suffixes are ordinary name text. For example, a new original a_1 whose candidate is already reserved may become a_1_1 , not automatically a_2 .
  • Calls and returned arrays may contain zero columns.

Example

calls = [["T","a.b","a_b","a_b_1"],
         ["T","a_b"],
         ["T","a_b_1","a.b","A.B"],
         ["U","a_b"]]
result = [["a_b","a_b_1","a_b_1_1"],
          ["a_b_1"],
          ["a_b_1_1","a_b","A_B_2"],
          ["a_b"]]

Explain why rebuilding names from only the current snapshot breaks stability, and how you handle a natural suffixed name colliding with an earlier generated name. Analyze repeated collision searches rather than assuming every new assignment is constant time.

Submit Your Answer to Earn 20XP

Sign in to leave a comment

Loading comments...