poj 1018 Communication System

题意:

某公司要建立一套通信系统,该通信系统需要n种设备,而每种设备分别可以有m1、m2、m3、...、mn个厂家提供生产,而每个厂家生产的同种设备都会存在两个方面的差别:带宽bandwidths 和 价格prices。

现在每种设备都各需要1个,考虑到性价比问题,要求所挑选出来的n件设备,要使得B/P最大。

其中B为这n件设备的带宽的最小值,P为这n件设备的总价。


我们定义状态dp 【i】【j】 表示选择了前 i 个宽带其容量为 j 的最小费用。 

很容易得到转移方程 :dp【i】【j】=min(dp【i】【j】,dp【i-1】【k】+p);

注意选择 j 的时候的大小情况。

#include <iostream>
#include <cstdio>
#include <cstring>
#include <cmath>
#include <queue>
#include <map>
#include <algorithm>
#define INF 0x3f3f3f3f
using namespace std;

typedef long long LL;

const int MAX = 1e5+10;

int Dp[120][1200];//买i件设备时,最小值为k时的花费

int main()
{
   
int n,T,m,b,p;
   
scanf("%d",&T);
   
while(T--)
    {
       
scanf("%d",&n);
       
memset(Dp,INF,sizeof(Dp));
       
for(int i=0;i<=1200;i++)//当没有一件设备是,自然p为零
        {
            Dp[
0][i]=0;
        }
       
for(int i=1;i<=n;i++)
        {
           
scanf("%d",&m);
           
for(int j=1;j<=m;j++)
            {
               
scanf("%d %d",&b,&p);
               
for(int k=0;k<1200;k++)
                {
                   
if(b<=k)//当买的b值比k值小时,说明在你买的设备中最小的为b,所以在买i-1件设备中花费+p与Dp[i][b]取小值
                    {
                        Dp[i][b]=min(Dp[i-
1][k]+p,Dp[i][b]);
                    }
                   
else
                    {
                        Dp[i][k]=min(Dp[i][k],Dp[i-
1][k]+p);//买的b值比k值大时,k是买的设备中的最小值,同理
                    }
                }
            }
        }
       
double ans=0;
       
for(int i=1;i<1200;i++)
        {
           
if(Dp[n][i]!=INF)
            {
               
if(ans<(i*1.0/Dp[n][i]))//遍历找出b/p的最大值
                {
                    ans=(i*
1.0/Dp[n][i]);
                }
            }
        }
       
printf("%.3f\n",ans);
    }

   
return 0;
}

猜你喜欢

转载自blog.csdn.net/yihanyifan/article/details/80136990