Watch 10 video solutions for Rearrange Products Table, a easy level problem involving Database. This walkthrough by Everyday Data Science has 7,805 views views. Want to try solving it yourself? Practice on FleetCode or read the detailed text solution.
Table: Products
+-------------+---------+ | Column Name | Type | +-------------+---------+ | product_id | int | | store1 | int | | store2 | int | | store3 | int | +-------------+---------+ product_id is the primary key (column with unique values) for this table. Each row in this table indicates the product's price in 3 different stores: store1, store2, and store3. If the product is not available in a store, the price will be null in that store's column.
Write a solution to rearrange the Products table so that each row has (product_id, store, price). If a product is not available in a store, do not include a row with that product_id and store combination in the result table.
Return the result table in any order.
The result format is in the following example.
Example 1:
Input: Products table: +------------+--------+--------+--------+ | product_id | store1 | store2 | store3 | +------------+--------+--------+--------+ | 0 | 95 | 100 | 105 | | 1 | 70 | null | 80 | +------------+--------+--------+--------+ Output: +------------+--------+-------+ | product_id | store | price | +------------+--------+-------+ | 0 | store1 | 95 | | 0 | store2 | 100 | | 0 | store3 | 105 | | 1 | store1 | 70 | | 1 | store3 | 80 | +------------+--------+-------+ Explanation: Product 0 is available in all three stores with prices 95, 100, and 105 respectively. Product 1 is available in store1 with price 70 and store3 with price 80. The product is not available in store2.
Problem Overview: You are given a Products table where each row contains a product_id and multiple store columns (store1, store2, store3). The task is to transform this wide table into a normalized row format: each non-null store price becomes a separate row with columns product_id, store, and price. This is essentially an unpivot operation commonly seen in database transformations.
Approach 1: Iterative Row and Column Traversal (O(n*k) time, O(1) extra space)
Treat the table like a small matrix: iterate through each product row, then check each store column individually. For every store field (store1, store2, store3), verify whether the value is non-null. When a price exists, emit a new row containing the product_id, the store name, and the price. The key insight is that the number of store columns is fixed and small, so a simple nested traversal works efficiently. This approach maps naturally to languages like Python or C# where you loop through rows and manually construct the output records. Time complexity is O(n*k), where n is the number of products and k is the number of store columns. Extra space is O(1) beyond the output since you only track the current row and column being processed. The pattern resembles iterating over a matrix with conditional filtering.
Approach 2: SQL-like Transformation with Language Features (O(n*k) time, O(k) space)
This approach models the solution after SQL UNPIVOT behavior using built-in language features. Create a small structure (array, map, or list) that pairs store names with their corresponding column values for each row. For example, convert a row into something like [("store1", value1), ("store2", value2), ("store3", value3)]. Iterate through this structure and append an output record whenever the value is not null. Languages like JavaScript or C make this clean by storing the store names in an array and iterating through them dynamically. The main insight is separating column metadata (store names) from row data, which simplifies the transformation logic. Time complexity remains O(n*k) since every product checks every store column. Space complexity is O(k) for the temporary store mapping used during each iteration. This style mirrors transformations commonly used in array-driven data reshaping pipelines.
Recommended for interviews: The iterative row and column traversal approach is typically expected. It clearly shows you understand how to normalize wide data structures by scanning each column and filtering null values. Demonstrating the SQL-style transformation afterward shows deeper familiarity with data reshaping patterns and how unpivot operations are implemented outside SQL engines.
| Approach | Time | Space | When to Use |
|---|---|---|---|
| Iterative Row and Column Traversal | O(n*k) | O(1) | Best when the number of store columns is small and fixed; simple and interview-friendly. |
| SQL-like Transformation with Language Features | O(n*k) | O(k) | Useful when implementing generic column-to-row transformations or mimicking SQL UNPIVOT behavior. |