• 【算法竞赛入门经典】7.3子集生成【增量构造法】【位向量法】【二进制法】


    7.3.1增量构造法

    思路:一次选出一个元素放到集合中。自己对于递归的理解还是不够,这里虽然没有明确给出递归停止条件,但是如果无法继续添加元素,就不会再继续递归,然后就是我头疼的回溯啦。

    #include<stdio.h>
    
    int num[4],n;
    
    void A(int n,int *a,int ans)
    {
        for(int i = 0; i < ans; i ++)//打印当前元素 
            printf("%d ",a[i]);
        printf("
    ");
        int s = ans?a[ans-1]+1:0;//确定当前元素的最小可能值 
        for(int i = s; i < n; i ++)
        {
            a[ans] = i;
            A(n,a,ans+1);//递归构造子集 
        } 
        return;
    }
    
    int main()
    {
        n = 3;
        A(n,num,0);
        return 0;
    }

    7.3.2位向量法

    思路:构造一个位向量a[i],如果a[i]=1,当且仅当i在集合子集a中。

    #include<stdio.h>
    int num[4],n;
    
    void print_subset(int n,int *a,int ans)
    {
        if(ans == n)
        {
            for(int i = 0; i < ans; i ++)//打印当前集合 
                if(a[i])
                    printf("%d ",i);
            printf("
    ");
            return;
        }
        a[ans] = 1;//选择第cur个元素 
        print_subset(n,a,ans+1);
        a[ans] = 0;//不选第cur个元素 
        print_subset(n,a,ans+1);
        return;
    }
    int main()
    {
        n = 3;
        print_subset(n,num,0);
        return 0;
    }

    7.3.3二进制法

    #include<stdio.h>
    int n = 3;
    void print_subset(int n,int ans)
    {
        for(int i = 0; i < n; i ++)//打印{0,1,2,3..n-1}的子集ans 
            if(ans&(1<<i))
                printf("%d ",i);
        printf("
    ");
        return;
    }
    
    int main()
    {
        for(int i = 0; i < (1<<n); i ++)//枚举各子集对应的编码 
            print_subset(n,i);
        return 0;
    }
  • 相关阅读:
    CentOS6、CentOS7配置Base源和epel源
    谢孟媛_初级英文文法_讲义!全!!
    java动态代理实现与原理详细分析
    聊聊spring的那些扩展机制
    springboot+druid+mybatis plus的多数据源配置
    基于CAS实现SSO单点登录
    mybatisPlus整理
    Python实现1-100之和
    python接口自动化--get请求
    使用fiddler进行接口测试
  • 原文地址:https://www.cnblogs.com/hellocheng/p/7449400.html
Copyright © 2020-2023  润新知