zoukankan      html  css  js  c++  java
  • P1156 垃圾陷阱

    传送门

    思路:

      设 f [ i ][ j ] 表示,扔进去 i 个垃圾,垃圾高度为 j 时,奶牛的生命值。

      初始化 f 数组为 -1,因为当奶牛生命值为 0 时,奶牛还是可以操纵垃圾。f [ 0 ][ 0 ] = 10 为奶牛的初始生命值。

      转移如下:

      ① 当 f [ i ][ j ] < 0 时,说明这个状态奶牛已经死了,跳过。

      ② 当 f [ i ][ j ] = 0 时,奶牛处于濒死状态,还可以操作,必须吃掉垃圾。进而判断这个垃圾恢复的生命值是否能够支撑到下一个垃圾的投入,若不能,就跳过,否则就转移状态。

      ③ 当 f [ i ][ j ] > 0 时,判断奶牛不吃这个垃圾的生命值能否支撑到下一个垃圾的投入,能,就把垃圾堆起来。不能,就吃掉。吃掉后再判断能否转移,同 ② 。

    伪代码:

    struct hh
    {
        LL tim,w,h;//tim垃圾投入的时间、w垃圾恢复的生命值、h垃圾的高度 
    }t[maxn];
    f[0][0]=10;
    for(LL i=0;i<g;i++)//第一重循环,枚举投入的垃圾 
        for(LL j=0;j<=d;j++)//枚举高度 
        {
            if(f[i][j]<0) continue;//如果奶牛无法到达这个状态,跳过 
            if(j+t[i+1].h>=d&&f[i][j]>=t[i+1].tim-t[i].tim)//判断奶牛在不吃这个垃圾的状态下,能否跳出陷阱 
            {
                out(t[i+1].tim);return 0;
            }
            if(f[i][j]-t[i+1].tim+t[i].tim>=0)//同时判断、转移②,③两种情况 
            {
                f[i+1][j+t[i+1].h]=f[i][j]-t[i+1].tim+t[i].tim;
                f[i+1][j]=lck_max(f[i+1][j],f[i][j]-t[i+1].tim+t[i].tim+t[i+1].w);
            }
        }

    标程:

    #include<iostream>
    #include<cstdio>
    #include<algorithm>
    #include<cmath>
    #include<cstring>
    #include<string>
    #include<cstdlib>
    #include<stack>
    #include<vector>
    #include<queue>
    #include<deque>
    #include<map>
    #include<set>
    using namespace std;
    #define lck_max(a,b) ((a)>(b)?(a):(b))
    #define lck_min(a,b) ((a)<(b)?(a):(b))
    typedef long long LL;
    #define maxn 1001
    LL d,g,ans,las,f[maxn][maxn];
    struct hh
    {
        LL w,h,tim;
    }t[maxn];
    inline LL read()
    {
        LL kr=1,xs=0;
        char ls;
        ls=getchar();
        while(!isdigit(ls))
        {
            if(!(ls^45))
                kr=-1;
            ls=getchar();
        }
        while(isdigit(ls))
        {
            xs=(xs<<1)+(xs<<3)+(ls^48);
            ls=getchar();
        }
        return xs*kr;
    }
    inline void out(LL xs)
    {
        if(!xs) {putchar(48); return;}
        if(xs<0) putchar('-'),xs=-xs;
        int kr[57],ls=0;
        while(xs) kr[++ls]=xs%10,xs/=10;
        while(ls) putchar(kr[ls]+48),ls--;
    }
    inline bool cmp(const hh&a,const hh&b)
    {
        return a.tim<b.tim;
    }
    int main()
    {
        freopen("ljxj.in","r",stdin);
        freopen("ljxj.out","w",stdout);
        d=read();g=read();
        for(LL i=1;i<=g;i++)
        {
            t[i].tim=read();t[i].w=read();t[i].h=read();
        }
        sort(t+1,t+g+1,cmp);
        memset(f,-1,sizeof(f));
        f[0][0]=10;
        for(LL i=0;i<g;i++)
            for(LL j=0;j<=d;j++)
            {
                if(f[i][j]<0) continue;
                if(j+t[i+1].h>=d&&f[i][j]>=t[i+1].tim-t[i].tim)
                {
                    out(t[i+1].tim);return 0;
                }
                if(f[i][j]-t[i+1].tim+t[i].tim>=0)
                {
                    f[i+1][j+t[i+1].h]=f[i][j]-t[i+1].tim+t[i].tim;
                    f[i+1][j]=lck_max(f[i+1][j],f[i][j]-t[i+1].tim+t[i].tim+t[i+1].w);
                }
            }
        for(LL i=1;i<=g;i++)
        {
            if(t[i].tim-t[i-1].tim>f[0][0])
                break;
            ans+=t[i].tim-t[i-1].tim;
            f[0][0]-=t[i].tim-t[i-1].tim;
            f[0][0]+=t[i].w;
        }
        ans+=f[0][0];
        out(ans);
    return 0;
    }
  • 相关阅读:
    python进阶之装饰器之3利用装饰器强制函数上的类型检查
    python进阶之装饰器之6.装饰器为被包装函数增加参数,如何实现装饰器对类进行打补丁或者说对类的功能进行扩充
    python进阶之装饰器之5把装饰器作用到类和静态方法上
    python进阶之装饰器之4在类中定义装饰器,将装饰器定义为类,两者的区别与联系
    AOP的使用
    使用Maven搭建SSM框架
    js判断字符串是否有重复
    纯js实现复制功能
    关于Log文本的操作
    jquery往textarea鼠标光标选中的地方插入值
  • 原文地址:https://www.cnblogs.com/lck-lck/p/9831263.html
Copyright © 2011-2022 走看看