• 希望 线段树 01背包


      

    链接:https://ac.nowcoder.com/acm/contest/917/E
    来源:牛客网

    题目描述

    水宝宝驾驶着毁灭号接近了勇者号舰桥。

    他要使用毁灭号的等离子炮摧毁勇者号主控台。

    但是操控等离子炮的程序出了点问题。等离子炮有n个操作信号,第i个操作信号的强度为b[i]。总体强度为各操作信号的强度之和。

    由于有些信号太弱了了 (强度<0),水宝宝想把它们删除。但是水宝宝自己不会删除信号,所以他找来了同船的队友帮忙。

    有 m位队友,第ii 位队友只会删除编号在 L[i] 和 R[i]之间的信号,且每删除一个信号,花费 C[i]格能量。飞船一共有 k格能量,问他在请队友删除完信号后,总体强度最大是多少。
     
     
    其实就是一个01背包  但是删除的代价 w 是有很多的(很多人的叠加)  只需要用线段树维护最小代价  然后再01背包一次就可以了
    #include<bits/stdc++.h>
    using namespace std;
    //input by bxd
    #define rep(i,a,b) for(int i=(a);i<=(b);i++)
    #define repp(i,a,b) for(int i=(a);i>=(b);--i)
    #define RI(n) scanf("%d",&(n))
    #define RII(n,m) scanf("%d%d",&n,&m)
    #define RIII(n,m,k) scanf("%d%d%d",&n,&m,&k)
    #define RS(s) scanf("%s",s);
    #define ll long long
    #define pb push_back
    #define inf 0x3f3f3f3f
    #define CLR(A,v)  memset(A,v,sizeof A)
    //////////////////////////////////
    const int N=1e5+5;
    int sum[N<<2],col[N<<2],w[N],c[N],k,m,n,dp[N],ans;
    #define lson l,m,pos<<1
    #define rson m+1,r,pos<<1|1
    
    void up(int pos)
    {
        sum[pos]=min(sum[pos<<1],sum[pos<<1|1]);
    }
    void down(int pos)
    {
        sum[pos<<1]=min(sum[pos<<1],col[pos]);
        sum[pos<<1|1]=min(sum[pos<<1|1],col[pos]);
        col[pos<<1]=min(col[pos<<1],col[pos]);
        col[pos<<1|1]=min(col[pos<<1|1],col[pos]);
        col[pos]=inf;
    }
    void build(int l,int r,int pos)
    {
        col[pos]=inf;
        if(l==r)
        {
            sum[pos]=inf;
            return ;
        }
        int m=(l+r)>>1;
        build(lson);
        build(rson);
        up(pos);
    }
    void update(int L,int R,int v,int l,int r,int pos)
    {
        if(L<=l&&r<=R)
        {
            sum[pos]=min(sum[pos],v);
            col[pos]=min(col[pos],v);
            return ;
        }
        down(pos);
        int m=(l+r)>>1;
        if(L<=m)update(L,R,v,lson);
        if(R>m)update(L,R,v,rson);
        up(pos);
    }
    void query(int L,int R,int l,int r,int pos)
    {
        if(l==r)
        {
            w[l]=sum[pos];
            return ;
        }
        int m=(l+r)>>1;
        down(pos);
        if(L<=m)query(L,R,lson);
        if(R>m)query(L,R,rson);
        up(pos);
    }
    int main()
    {
        RIII(n,k,m);
        rep(i,1,n)RI(c[i]),ans+=c[i];
    
        build(1,n,1);
        rep(i,1,m)
        {
            int u,w,v;
            RIII(u,w,v);
            update(u,w,v,1,n,1);
        }
        query(1,n,1,n,1);
    
        rep(i,1,n)
        repp(j,k,0)
        if(j>=w[i])
        dp[j]=max(dp[j],dp[j-w[i]]-c[i]);
    
        cout<<ans+dp[k];
    
        return 0;
    }
    View Code
     
     
     
     
     
  • 相关阅读:
    java 笔记(6) static关键字
    java 笔记(5)接口,static
    java 笔记(4)抽象类与抽象方法
    java 笔记(3)多态 容易理解
    看穿CSS的定位技术
    揭开浮动布局的秘密(简略版)
    不可不知的CSS盒子模型(简略版)
    初学Java web 项目
    Eclipse快捷键
    JDBC连接数据库
  • 原文地址:https://www.cnblogs.com/bxd123/p/11027224.html
Copyright © 2020-2023  润新知