function subsets(nums: number[]): number[][] {
const result: number[][] = [];
nums.sort((a, b) => a - b);
function backtrack(start: number, path: number[]) {
result.push([...path]);
for (let i = start; i < nums.length; i++) {
if (i > start && nums[i] === nums[i - 1]) continue;
path.push(nums[i]);
backtrack(i + 1, path);
path.pop();
}
}
backtrack(0, []);
return result;
}
console.log(subsets([1, 2, 2]));The code sorts the input array and uses backtracking to generate subsets. It skips duplicates by checking if the current number is the same as the previous one at the same recursion level. This ensures unique subsets only.
The output includes the empty subset, subsets with one element, and subsets with duplicates only once.
Each element has two choices: to be in or out of a subset. So total subsets = 2 * 2 * ... * 2 (n times) = 2^n.
The code pushes the same array reference 'path' into the result multiple times. Since 'path' is mutated later, all entries in result point to the same final array state.
To fix, push a copy of 'path' using [...path].
function subsets(nums: number[]): number[][] {
const result: number[][] = [[]];
for (const num of nums) {
const newSubsets = result.map(subset => [...subset, num]);
result.push(...newSubsets);
}
return result;
}
console.log(subsets([1, 2]));The code starts with [[]]. For each number, it creates new subsets by adding the number to all existing subsets and appends them.
For [1,2], subsets are [], [1], [2], [1,2] in that order.
There are 2^n subsets. Each subset can have up to n elements. Copying each subset takes O(n) time.
So total time is O(n * 2^n).