子集
给你一个整数数组 nums ,数组中的元素 互不相同 。返回该数组所有可能的子集(幂集)。
解集 不能 包含重复的子集。你可以按 任意顺序 返回解集。
示例 1:
输入:nums = [1,2,3]
输出:[[],[1],[2],[1,2],[3],[1,3],[2,3],[1,2,3]]
示例 2:
输入:nums = [0]
输出:[[],[0]]
提示:
1 <= nums.length <= 10
-10 <= nums[i] <= 10
nums 中的所有元素 互不相同
来源:力扣(LeetCode)
链接:https://leetcode.cn/problems/subsets
著作权归领扣网络所有。商业转载请联系官方授权,非商业转载请注明出处。
解题思路1
子集就是数组中所有元素的集合加上一个空集构成的集合。求解组合和排列实际上就是DFS一棵树的过程。写此类题目画一棵树再根据树来写dfs即可。树可见代码注释。可以看到树的下一层是从上一层的下一个元素开始的。
code
class Solution {
public:
//组合加上空集就是子集
//如何求解所有的组合,DFS
//想想一个求解组合的递归树并通过树来写递归的算法
//1 -> 2 -> 3
// -> 3
//2 -> 3
//3
vector<vector<int> > ans;
int n;
void dfs(vector<int> & nums,int start,vector<int>& path)
{
for(int i = start;i < n;i ++)
{
path.push_back(nums[i]);
ans.push_back(path);
dfs(nums,i + 1,path);
path.pop_back();
}
}
vector<vector<int>> subsets(vector<int>& nums) {
n = nums.size();
vector<int> path;
ans.push_back({});
dfs(nums,0,path);
return ans;
}
};
解题思路2
可以使用二进制位表示当前位置的数组元素是否被选择。比如000表示三个元素都没有被选择,001表示1位置的元素被选择。如果有n位实际上就是有种可能,只需要遍历0-可能性即可。
code
class Solution {
public:
//位运算:对应位置1即为选用
//遍历2 ^ n -1 中可能即可
vector<vector<int>> subsets(vector<int>& nums) {
vector<vector<int>> ans;
int n = nums.size();
for(int mask = 0;mask < (1 << n);mask ++)
{
vector<int> sub;
for(int i = 0;i < n;i ++)
{
if(mask & (1 << i)) sub.push_back(nums[i]);
}
ans.push_back(sub);
}
return ans;
}
};
【推荐】国内首个AI IDE,深度理解中文开发场景,立即下载体验Trae
【推荐】编程新体验,更懂你的AI,立即体验豆包MarsCode编程助手
【推荐】抖音旗下AI助手豆包,你的智能百科全书,全免费不限次数
【推荐】轻量又高性能的 SSH 工具 IShell:AI 加持,快人一步
· 被坑几百块钱后,我竟然真的恢复了删除的微信聊天记录!
· 没有Manus邀请码?试试免邀请码的MGX或者开源的OpenManus吧
· 【自荐】一款简洁、开源的在线白板工具 Drawnix
· 园子的第一款AI主题卫衣上架——"HELLO! HOW CAN I ASSIST YOU TODAY
· Docker 太简单,K8s 太复杂?w7panel 让容器管理更轻松!