排列组合-生成集合的所有子集

 //一个有N个不重复元素的集合的某个子集,可以用这个N个元素中每个元素在或是不在这个子集中来表示。
//把这N个元素一字排开,每个位置可以用1来标识对应位置的元素在子集中,用0来标识这个元素不在子集中
//依据计数的乘法原理这样的排列数有2^N个,也就是一个有N个不重复元素的集合有2^N个子集。
//而这种10表示方式刚好与N元的二进制串一一对应。
public class CombinationAll
{
    public static void main(String[] args)
    {
        //指定集合的元素个数N
        int N=Integer.parseInt(args[0]);
        //使用一个长度为N的一维数组来表示N元的2进制串
        int[] bin=new int[N];
        //并从00...000开始,到11..111结束。
        //由于检查11...111会花费较多的比较,改用计数器来实现。
        for(int i=0;i<N;i++)
            bin[i]=0;
        show(bin);
        //计数器标识还剩多少个子集没有列出
        double Total=Math.pow(2,N)-1;
        //二进制串每次增加1,计数器每次减1
        int i;
        while(Total>0)
        {
            //从低位向高位找到第一个0,然后将这个0变成1,将这个位置后面的1全变成0
            for(i=N-1;i>=0 && bin[i]==1;i--)
                bin[i]=0;
            bin[i]=1;
            show(bin);
            Total--;
        }
    }
   
    //显示这个数组中的二进制串
    private static void show(int[] bin)
    {
        for(int i=0;i<bin.length;i++)
            StdOut.printf("%d",bin[i]);
        StdOut.println();
    }
}

posted @ 2018-10-29 08:29  修电脑的龙生  阅读(462)  评论(0编辑  收藏  举报