• hdu 4314 Save the dwarfs 夜


    http://acm.hdu.edu.cn/showproblem.php?pid=4314

    典型的动态规划   首先要确认一点 那就是假设有一定数量的小矮人逃了出去 那么

    先逃出去的小矮人 身高+臂长  一定比后逃出的小矮人 身高+臂长  要短  这样才能最优(这个还是看了解析才知道的)

    当最顶端的小矮人可以逃出去的话 他可以选择逃或者不逃 如果逃不出去就一定不逃 

    要注意的是如果他不逃 就会对后面的小矮人逃走造成一些好的影响 由于他的身高影响(把他放在最下面)会使后面的小矮人更容易接近洞口

    处理就在这里 要想办法把这种好的影响记录下来。

    假设最 身高+臂长 最大的小矮人 i 值最大

    ans[i][j]  表示到第 i 个小矮人逃出去了 j 个人时  可以对后面的小矮人造成的最大好处

    如果为 最负(很小的负数) 值则表示无这种情况

    找第n个小矮人时 满足要求的最多人逃出

    代码及其注释:

    #include<iostream>
    #include<cstring>
    #include<algorithm>
    #include<cstdio>
    
    using namespace std;
    
    const int N=2005;
    const int MIN=-1000000000;
    struct node
    {
        int a,b;
    }mem[N];
    int L[N];
    int ans[N][N];
    int H;
    bool cmp(node x,node y)
    {
        return x.a+x.b<y.a+y.b;
    }
    int dp(int x,int num)
    {
        if(ans[x][num]!=-1)//你懂得
        return ans[x][num];
        if(x==0)//第0 个人
        {
            if(num==0)
            ans[x][num]=0;//如果让逃出0个人 则可以 可以造成0个好的影响
            else
            ans[x][num]=MIN;//否则不存在这种情况 最小负数
            return ans[x][num];
        }
        if(num==0)
        {
            ans[x][num]=mem[x].a+dp(x-1,num);//如果需要逃出0个人 则可以直接把x小矮人的身高加在好的影响点上
            return ans[x][num];
        }
        ans[x][num]=MIN;//先赋值最小负数
        if(dp(x-1,num-1)+mem[x].b+L[x]>=H)//如果存在他可以逃出的情况
        {
            ans[x][num]=dp(x-1,num-1);//记录值
        }
        ans[x][num]=max(ans[x][num],dp(x-1,num)+mem[x].a);//查看x小矮人不逃出去时 是否最优
        return ans[x][num];
    }
    int main()
    {
        int n;
        while(scanf("%d",&n)!=EOF)
        {
            for(int i=1;i<=n;++i)
            {
                scanf("%d %d",&mem[i].a,&mem[i].b);
            }
            scanf("%d",&H);
            sort(mem+1,mem+n+1,cmp);//根据身高+臂长 从小到大排序
            L[n+1]=0;
            for(int i=n;i>=1;--i)
            L[i]=L[i+1]+mem[i].a;//从数组后面开始累加身高的和
    
            memset(ans,-1,sizeof(ans));
            for(int i=n;i>=0;--i)
            {
                if(dp(n,i)>=0)
                {
                    printf("%d\n",i);//满足要求的最大 逃出人数
                    break;
                }
            }
        }
        return 0;
    }
    

      

  • 相关阅读:
    SEO(Business)
    C#数组去掉重复的元素
    文件创建与文件格式的修改
    Filter(20160815)
    OmniGraffle导入stencils的两个方法以及优质的stencils下载网站推荐
    在Axure RP 8.0 中使用 Font Awesome 图标库完成设计并能在其他未安装该字体的电脑离线预览的方法
    社会性动物(艾略特•阿伦森)
    MacTex 在XeLaTex编译状态下插入的pdf格式图片无法显示问题的解决方案
    Markdown,别来无恙!
    男人来自火星 女人来自金星(约翰·格雷)
  • 原文地址:https://www.cnblogs.com/liulangye/p/2612441.html
Copyright © 2020-2023  润新知