一个List的所有子集

假设有一个list [1,2,3],要求出list的所有子集!

假设一个list的长度为n,那么它就包含 2^n 个子集(包含空集)。同样的,1个长度为 n 的二进制字符串,可以表示 2^n 个数。

所以我们不难联想到,要求list的子集,其实就是位运算:

[ ]     ——> 0 0 0   ——> 0

[1]     ——> 1 0 0   ——> 4

[2]     ——> 0 1 0   ——> 2

[3]     ——> 0 0 1   ——> 1

[1,2]   ——> 1 1 0   ——> 6

[1,3]   ——> 1 0 1   ——> 5

[2,3]   ——> 0 1 1   ——> 3

[1,2,3] ——> 1 1 1   ——> 7

所以要得到长度为 n 的list的子集,只需要遍历从 0—2^n-1 ,然后转化成二进制,把对应位置为 1 的数字放入集合。

十进制转二进制:

因为我使用的是Java,在Java中有现成的语句能够调用:

int a = 8
b = Integer.toBinaryString(a);

输出:b = "1000"

当然也可以按照二进制的定义自己写:

    public int toBinary(int num) {
    int r = 0;
    int k = 1;
    int sum = 0;
    	while(num != 0) {
    		r = num % 2;
    		sum += r*k;
    		k *= 10;
    		num /= 2;
    	}
    	return sum;
    }

完整代码(Java):

public List<List<Integer>> subsets(int[] nums) {
    List<List<Integer>> sets = new ArrayList<List<Integer>>();
    for(int i=0;i<=Math.pow(2, nums.length)-1;i++) {
    	List<Integer> list = new ArrayList<Integer>();
    	String a = Integer.toBinaryString(i); //转化为二进制
        for(int j=0;j<a.length();j++) {
        	char c = a.charAt(j); //取到String中的每个字符
        	if(c == '1') list.add(nums[nums.length-a.length()+j]); //把对应位置为1的数字放入集合
        }
    sets.add(list);
    }
    return sets;
 }

猜你喜欢

转载自blog.csdn.net/qq_38310176/article/details/81144970