zoukankan      html  css  js  c++  java
  • hdu 2079(01背包+多重背包或者用母函数)

    题意:易理解...

    分析:01背包+多重背包,主要思考的是如何避免重复,因为是01背包所以我把同种类型的物品一次装入一个背包里,自己好好思考吧!!这道题挺好的!!!当然用母函数也容易理解,母函数更好理解吧!!

    代码实现:

    背包实现:
    #include<stdio.h>//可以说是01背包+多重背包 #include<string.h> int main() { int T,n,m,i,j,k; int a[10],num[10],dp[45]; scanf("%d",&T); while(T--) { scanf("%d%d",&n,&m); for(i=1;i<=m;i++) scanf("%d%d",&a[i],&num[i]); for(i=1;i<=n;i++) dp[i]=0; dp[0]=1; for(i=1;i<=m;i++) for(j=n;j>=a[i];j--) for(k=1;k<=num[i]&&(j-a[i]*k)>=0;k++)//这个for循环用于避免重复,设置很巧妙,想了很久啊 dp[j]=dp[j]+dp[j-a[i]*k];//就是把一个物品的每种情况都装进容量固定的包里,这里就会避免重复 printf("%d\n",dp[n]); } return 0; }
    母函数实现:
    #include<stdio.h>
    #include<string.h>
    int c1[10001],c2[10001];//c1用来记录各项的系数,也就是方案数,c2是用来临时存储的
    int main()
    {
        int i,j,k,T,n,m,a[10],num[10],t;
        scanf("%d",&T);
        while(T--)
        {
            scanf("%d%d",&n,&m);
            for(i=1;i<=m;i++)
                scanf("%d%d",&a[i],&num[i]);
            memset(c1,0,sizeof(c1));
            for(i=0,t=0;i<=n&&t<=num[1];i=i+a[1],t++)
                c1[i]=1;
            for(i=0;i<=n;i++)
                c2[i]=0;
            for(i=2;i<=m;i++)
            {
               for(j=0;j<=n;j++)
                   for(k=0,t=0;k+j<=n&&t<=num[i];k=k+a[i],t++)
                       c2[j+k]=c1[j]+c2[j+k];   
               for(j=0;j<=n;j++)
               {
                   c1[j]=c2[j];
                   c2[j]=0;
               }
            }
            printf("%d\n",c1[n]);
        }
        return 0;
    }
  • 相关阅读:
    C# 文件类的操作---删除
    C#实现Zip压缩解压实例
    UVALIVE 2431 Binary Stirling Numbers
    UVA 10570 meeting with aliens
    UVA 306 Cipher
    UVA 10994 Simple Addition
    UVA 696 How Many Knights
    UVA 10205 Stack 'em Up
    UVA 11125 Arrange Some Marbles
    UVA 10912 Simple Minded Hashing
  • 原文地址:https://www.cnblogs.com/jiangjing/p/3010802.html
Copyright © 2011-2022 走看看