• poj1853


    题意:给一堆物品分成两堆,两堆总重量相差不到百分之2。。。

     思路:本题是个好题。。很新颖的dp。。

            因为n与给定的数字都不超过100,且允许误差为2%,所以我们可以进行放大,把小数化成整数,这样就可以进行dp了。。具体是把所有总数看成20000粉,然后按比率分配。。分配为进行背包。。

    /*
      State:Accepted
      Time:2013-03-12 00:12:37
    */
    #include <iostream>
    #include <cstring>
    #include <string>
    #include <cstdlib>
    #include <cstdio>
    #include <algorithm>
    #include <cmath>
    #include <queue>
    using namespace std;
    struct oo{ int l, p , s; };
    int n , f[20010], g[20100], a[120],tm;
    float sum(0);
    void init()
    {    
         float b[120];
         sum = 0;
         memset(g,0,sizeof(g));
         memset(f,0,sizeof(f));
         memset(a,0,sizeof(a));
         for (int i = 1; i <= n; ++i)
            {
                   scanf("%f", &b[i]);
                   sum += b[i];
            }
         for (int i = 1; i <= n; ++i)
            a[i] = b[i]/sum * 20000;
    }
    
    void print(int now)
    {
         if (now == 0) return;
         int i = g[now];
         print(now - a[i]);
         printf("%d ",i); 
    }
    
    void dp()
    {
         f[0] = 1;
         for (int i = 1;  i <=n; ++i)
           for (int j = 10000; j >=0; --j)
             if (f[j] && !f[j + a[i]])
             {
                  f[j + a[i]] = 1;
                  g[j + a[i]] = i;
             }
         int i;
         for (i = 10000; i >= 0; --i)
            if (f[i]) break;
         print(i);
         printf("\n");
            
    }
    
    
    int main(){
         freopen("poj1853.in","r",stdin);
         freopen("poj1853.out","w",stdout);
         while (scanf("%d",&n)!=EOF && n)
           {
             init();
             dp();
           }
    }
  • 相关阅读:
    Document
    Document
    Document
    Document
    Document
    Document
    set常见操作:
    select 不存在字段,并设置默认值
    c#为字段设置默认值,以及构造函数初始化List对象。
    ThreadLocal
  • 原文地址:https://www.cnblogs.com/yzcstc/p/2977935.html
Copyright © 2020-2023  润新知