zoukankan      html  css  js  c++  java
  • 递归实现指数型枚举

    题目描述

    从 1~n 这 n 个整数中随机选取任意多个,输出所有可能的选择方案。

    输入格式

    输入一个整数n。

    输出格式

    每行输出一种方案。

    同一行内的数必须升序排列,相邻两个数用恰好1个空格隔开。

    对于没有选任何数的方案,输出空行。

    本题有自定义校验器(SPJ),各行(不同方案)之间的顺序任意。

    数据范围

    1(leq)n (leq) 15

    输入样例

    3

    输出样例

    3
    2
    2 3
    1
    1 3
    1 2
    1 2 3


    思路

    1~n这n个数字每个数字都有输出与不输出两种选择。所以所有的输出方案共有(2^n)种。
    我们可以考虑使用状态压缩的做法。
    状态压缩的特性:可以枚举所有选与不选的情况。
    可以用state的二进制表示形式中每位上的0/1体现每个数字的不选/选
    eg:
    当n=3时,共有8中输出方案。
    state=0 ——> 000 ——>一个数字也不输出
    state=1 ——> 001 ——>输出数字1
    state=2 ——> 010 ——>输出数字2
    state=3 ——> 011 ——>输出数字1 2
    state=4 ——> 100 ——>输出数字3
    state=5 ——> 101 ——>输出数字1 3
    state=6 ——> 110 ——>输出数字2 3
    state=7 ——> 111 ——>输出数字1 2 3

    非递归C++ 代码

    #include<iostream>
    using namespace std;
    int main()
    {
        ios::sync_with_stdio(false);
        cin.tie(0);
        int n;
        cin>>n;
        for(int state=0;state<(1<<n);state++)
        {
            for(int j=0;j<n;j++)
            {
                if(state>>j&1)
                cout<<j+1<<" ";
            }
            cout<<endl;
        }
        return 0;
    }
    

    递归C++ 代码

    #include<iostream>
    using namespace std;
    void dfs(int u,int state,int n)//state用来记录路径
    {
        if(u==n)
        {
            for(int i=0;i<n;i++)
            {
                if(state>>i&1)//如过state的二进制形式中的第i位是1
                {
                    cout<<i+1<<" ";
                }
            }
            cout<<endl;
            return;
        }
        dfs(u+1,state,n);//不选择第u个数字,此时state的二进制形式中第u位为0(注意是从0开始),并在此基础上进行第u+1个数字的深搜
        dfs(u+1,state|(1<<u),n);//选择第u个数字,此时将state的二进制形式中第u位改为1(注意是从0开始),并在此基础上进行第u+1个数字的深搜
    }
    int main()
    {
        ios::sync_with_stdio(false);
        cin.tie(0);
        int n;
        cin>>n;
        dfs(0,0,n);//从第0个数字开始进行深度优先搜索
        return 0;
    }
    

    非状压DP递归代码

    #include<iostream>
    using namespace std;
    int stu[20];
    void dfs(int u,int n)
    {
        if(u>n)
        {
            for(int i=1;i<=n;i++)
            {
                if(stu[i]==1)
                cout<<i<<" ";
            }
            cout<<endl;
            return;
        }
        stu[u]=1;
        dfs(u+1,n);
        stu[u]=0;
        stu[u]=2;
        dfs(u+1,n);
        stu[u]=0;
    }
    int main()
    {
        ios::sync_with_stdio(false);
        cin.tie(0);
        int n;
        cin>>n;
        dfs(1,n);
        return 0;
    }
    
  • 相关阅读:
    C# 基于密钥的64位加密与解密方法(原创)
    爱情 前途 命运
    设计模式学习笔记装饰模式
    jquery暂无图片插件
    IIS GZIP压缩(转)
    Fckeditor使用笔记
    设计模式学习笔记策略模式
    电子商务网站搜索架构方案
    批量修改数据库表的架构sql
    win 2003 安装 vs2005 sp1 问题1718
  • 原文地址:https://www.cnblogs.com/Acapplella/p/13548547.html
Copyright © 2011-2022 走看看