ICode9

精准搜索请尝试: 精确搜索
首页 > 其他分享> 文章详细

$HNOI2005$星际贸易

2019-11-06 21:52:44  阅读:298  来源: 互联网

标签:MF 问中 int while HNOI2005 贸易 星际 Now MYE


因为【数据删除】俺懒得写有趣的链接了

神\(TM\)的超多信息。。。

认真观察一波题面,我们发现第一问就是个背包,跑一遍就好了。

状态为\(f[i][j]\)表示前\(i\)个星球,卖了\(j\)吨的最大贸易额。

但是在第一问中的最优答案和第二问有关,具体来说是第一问中的中转移的点必选。

关于第二问,我们设\(f[i][j]\)表示到第\(i\)个星球,剩余\(j\)个燃料的最小花费。

根据买燃料和维修两种情况转移就好了。

\(f[i][j]=max(f[i][j-1]+P_i,f[k][j+2]+F_i)\)

显然这个转移是\(n^3\)的,我们通过\(yyb\)的博客发现有单调性,用单调队列维护即可。

注意遇到第一问中必须转移的点时队列清空。

#include<bits/stdc++.h>
using namespace std;
#define int long long
inline int read()
{
    int f=1,w=0;char x=0;
    while(x<'0'||x>'9') {if(x=='-') f=-1; x=getchar();}
    while(x!=EOF&&x>='0'&&x<='9') {w=(w<<3)+(w<<1)+(x^48);x=getchar();}
    return w*f;
}
const int N=2e3+10;
int n,MF,ML,m,J,JJ,Q[N<<1][N];
int f[N][N<<1],Vis[N<<1],H[N<<1],T[N<<1];
struct Planet
{
    int Out,Mon;
    int Dis,Amt,Fix;
} p[N];
signed main(){
#ifndef ONLINE_JUDGE
    freopen("A.in","r",stdin);
#endif
    n=read();m=read(),MF=read(),ML=read();
    if(MF>(n<<1)) MF=n<<1;
    for(int i=1;i<=n;i++)
    {
        p[i].Out=read(),p[i].Mon=read();
        p[i].Dis=read(),p[i].Amt=read(),p[i].Fix=read();
    }
    for(int i=1;i<=n;i++)
        if(p[i].Dis-p[i-1].Dis>ML){puts("Poor Coke!");return 0;}
    memset(f,0xf3,sizeof(f));f[0][0]=0;
    for(int i=1;i<=n;i++)
        for(int j=0;j<=m;j++)
        {
            if(j>=p[i].Out)
                f[i][j]=max(f[i-1][j],f[i-1][j-p[i].Out]+p[i].Mon);
            f[i][j]=max(f[i-1][j],f[i][j]);
        }
    for(int i=1;i<=m;i++) if(f[n][i]>f[n][J]) J=i;
    int MYE=f[n][J];
    for(int i=n,Now=J;i;i--)
        if(f[i][Now]!=f[i-1][Now])
            Vis[i]=1,Now-=p[i].Out;
    memset(f,0x3f,sizeof(f));
    f[0][MF]=0;Q[MF][T[MF]++]=0;
    //H[MF]=1;
    for(int i=1;i<=n;i++)
        for(int j=0;j<=MF;j++)
        {
            if(p[i].Amt&&j) f[i][j]=min(f[i][j],f[i][j-1]+p[i].Amt);
            if(T[j+2]>H[j+2]) f[i][j]=min(f[i][j],f[Q[j+2][H[j+2]]][j+2]+p[i].Fix);
            if(Vis[i]) H[j]=0,T[j]=0;
            while(H[j]<T[j]&&f[Q[j][T[j]-1]][j]>=f[i][j]) T[j]--;
            Q[j][T[j]++]=i;
            while(H[j]<T[j]&&p[i+1].Dis-p[Q[j][H[j]]].Dis>ML) H[j]++;
        }
    for(int j=1;j<=MF;j++) if(f[n][j]<f[n][JJ]) JJ=j;
    f[n][JJ]>=1e9?puts("Poor Coke!"):printf("%lld %lld",MYE,MYE-f[n][JJ]);
}

标签:MF,问中,int,while,HNOI2005,贸易,星际,Now,MYE
来源: https://www.cnblogs.com/wo-shi-zhen-de-cai/p/11808915.html

本站声明: 1. iCode9 技术分享网(下文简称本站)提供的所有内容,仅供技术学习、探讨和分享;
2. 关于本站的所有留言、评论、转载及引用,纯属内容发起人的个人观点,与本站观点和立场无关;
3. 关于本站的所有言论和文字,纯属内容发起人的个人观点,与本站观点和立场无关;
4. 本站文章均是网友提供,不完全保证技术分享内容的完整性、准确性、时效性、风险性和版权归属;如您发现该文章侵犯了您的权益,可联系我们第一时间进行删除;
5. 本站为非盈利性的个人网站,所有内容不会用来进行牟利,也不会利用任何形式的广告来间接获益,纯粹是为了广大技术爱好者提供技术内容和技术思想的分享性交流网站。

专注分享技术,共同学习,共同进步。侵权联系[81616952@qq.com]

Copyright (C)ICode9.com, All Rights Reserved.

ICode9版权所有