在处理前要对传入数组排序,不然返回的子集虽然对但和系统的顺序不一样导致不能Accepted。
java代码的一种递归的方式public class Solution {
/**
* @param nums: A set of numbers
* @return: A list of lists
*/
public List<List<Integer>> subsets(int[] nums) {
if(nums == null) {
return null;
}
Arrays.sort(nums);
List<List<Integer>> lists = new ArrayList<>();
for (int i = 1; i <= nums.length; i++) {
List<Integer> list = new ArrayList<>();
subsets(nums, 0, i, list, lists);
}
lists.add(new ArrayList<>());
return lists;
}
private void subsets(int[] nums, int s, int w, List<Integer> list, List<List<Integer>> lists) {
if (w == 0) {
return;
}
for (int i = s; i <= nums.length - w; ++i) {
List<Integer> set = new ArrayList<>(list);
set.add(nums[i]);
subsets(nums, i + 1, w - 1, set, lists);
if (1 == w) {
lists.add(set);
}
}
}
}
java非递归方式,1、先计算出m个元素的集合有多少组组合n,n=2的m次方,组合就是选和不选的情况,所以可以用二进制的1代表选0代表不选,架设有两个元素{1,2},则组合有00->{},10->{1},01->{2},11->{1,2},所以组合总数就为集合元素数量对应的二进制数的全排列种数(n=2^m),当然可以用公式C(m,m)=A(m,m)/m!计算。因为n个下标索引对应n种不同排列的二进制,所以用位移读取没个0-n的下标索引数的二进制每个位来设置每个子集。
private void subSet(int set[]) {
int length = set.length;
long n = (long) Math.pow((float) 2, length);
for (int i = 0; i < n; i++) {
System.out.print("{");
int temp = i;
for (int j = 0; j < length; j++) {
if ((temp & 1) == 1) {
System.out.print(set[j]);
if (j < length - 1) {
System.out.print(",");
}
}
temp = temp >> 1;
}
System.out.print("} ");
}
}