• BZOJ3252: 攻略


    3252: 攻略

    Time Limit: 10 Sec  Memory Limit: 128 MB
    Submit: 162  Solved: 52
    [Submit][Status]

    Description

    题目简述:树版[k取方格数]
     
    众所周知,桂木桂马是攻略之神,开启攻略之神模式后,他可以同时攻略k部游戏。
    今天他得到了一 款新游戏《XX半岛》,这款游戏有n个场景(scene),某些场景可以通过不同的选择支到达其他场景。所有场景和选择支构成树状结构:开始游戏时在根节 点(共通线),叶子节点为结局。每个场景有一个价值,现在桂马开启攻略之神模式,同时攻略k次该游戏,问他观赏到的场景的价值和最大是多少(同一场景观看 多次是不能重复得到价值的)
    “为什么你还没玩就知道每个场景的价值呢?”
    “我已经看到结局了。”

    Input

    第一行两个正整数n,k
    第二行n个正整数,表示每个场景的价值
    以下n-1行,每行2个整数a,b,表示a场景有个选择支通向b场景(即a是b的父亲)
    保证场景1为根节点

    Output

     
    输出一个整数表示答案

    Sample Input

    5 2
    4 3 2 1 1
    1 2
    1 5
    2 3
    2 4

    Sample Output

    10

    HINT

    对于100%的数据,n<=200000,1<=场景价值<=2^31-1

    Source

    题解:
    同学们都在复习我来机房是不是做死
    你们都这么强我却在这儿刷水是不是做死
    我们每次选一条最大权值的链,然后把经过该路径的点的权值都减去该点的权值,这个可以用dfs序+线段树来搞,因为每个点顶多被删1次,所以复杂度是nlogn的
    代码:
      1 #include<cstdio>
      2 
      3 #include<cstdlib>
      4 
      5 #include<cmath>
      6 
      7 #include<cstring>
      8 
      9 #include<algorithm>
     10 
     11 #include<iostream>
     12 
     13 #include<vector>
     14 
     15 #include<map>
     16 
     17 #include<set>
     18 
     19 #include<queue>
     20 
     21 #include<string>
     22 
     23 #define inf 100000000000000ll
     24 
     25 #define maxn 500000+5
     26 
     27 #define maxm 500+100
     28 
     29 #define eps 1e-10
     30 
     31 #define ll long long
     32 
     33 #define pa pair<int,int>
     34 
     35 #define for0(i,n) for(int i=0;i<=(n);i++)
     36 
     37 #define for1(i,n) for(int i=1;i<=(n);i++)
     38 
     39 #define for2(i,x,y) for(int i=(x);i<=(y);i++)
     40 
     41 #define for3(i,x,y) for(int i=(x);i>=(y);i--)
     42 
     43 #define mod 1000000007
     44 
     45 using namespace std;
     46 
     47 inline int read()
     48 
     49 {
     50 
     51     int x=0,f=1;char ch=getchar();
     52 
     53     while(ch<'0'||ch>'9'){if(ch=='-')f=-1;ch=getchar();}
     54 
     55     while(ch>='0'&&ch<='9'){x=10*x+ch-'0';ch=getchar();}
     56 
     57     return x*f;
     58 
     59 }
     60 ll n,m,tot,a[maxn],b[maxn],fa[maxn],id[maxn],l[maxn],r[maxn],ti,head[maxn];
     61 struct seg{int l,r;ll mx[2],tag;}t[4*maxn];
     62 struct edge{int go,next;}e[maxn];
     63 bool v[maxn];
     64 inline void insert(int x,int y)
     65 {
     66     e[++tot].go=y;e[tot].next=head[x];head[x]=tot;
     67 }
     68 inline void pushup(int k)
     69 {
     70     int l=k<<1,r=k<<1|1;
     71     t[k].mx[1]=0;
     72     if(t[l].mx[1]>t[k].mx[1])t[k].mx[1]=t[l].mx[1],t[k].mx[0]=t[l].mx[0];
     73     if(t[r].mx[1]>t[k].mx[1])t[k].mx[1]=t[r].mx[1],t[k].mx[0]=t[r].mx[0];
     74 }
     75 void build(int k,int l,int r)
     76 {
     77     t[k].l=l;t[k].r=r;int mid=(l+r)>>1;
     78     if(l==r){t[k].mx[0]=l;t[k].mx[1]=b[id[l]];return;}
     79     build(k<<1,l,mid);build(k<<1|1,mid+1,r);
     80     pushup(k);
     81 }
     82 inline void update(int k,ll z)
     83 {
     84     t[k].mx[1]-=z;
     85     t[k].tag+=z;
     86 }
     87 inline void pushdown(int k)
     88 {
     89     if(!t[k].tag)return;
     90     update(k<<1,t[k].tag);
     91     update(k<<1|1,t[k].tag);
     92     t[k].tag=0;
     93 }
     94 void add(int k,int x,int y,ll z)
     95 {
     96     int l=t[k].l,r=t[k].r,mid=(l+r)>>1;
     97     if(l==x&&r==y){update(k,z);return;}
     98     pushdown(k);
     99     if(y<=mid)add(k<<1,x,y,z);
    100     else if(x>mid)add(k<<1|1,x,y,z);
    101     else add(k<<1,x,mid,z),add(k<<1|1,mid+1,y,z);
    102     pushup(k);
    103 }
    104 void dfs(int x)
    105 {
    106     id[l[x]=++ti]=x;
    107     for(int i=head[x];i;i=e[i].next)
    108     {
    109         int y=e[i].go;
    110         b[y]=b[x]+a[y];
    111         dfs(y);
    112     }
    113     id[r[x]=++ti]=x;
    114 }
    115 
    116 int main()
    117 
    118 {
    119 
    120     freopen("input.txt","r",stdin);
    121 
    122     freopen("output.txt","w",stdout);
    123 
    124     n=read();m=read();
    125     for1(i,n)a[i]=read();
    126     for1(i,n-1){int x=read(),y=read();fa[y]=x;insert(x,y);}
    127     b[1]=a[1];
    128     dfs(1);
    129     build(1,1,2*n);
    130     ll ans=0;
    131     for1(i,m)
    132     {
    133         ans+=t[1].mx[1];
    134         for(int j=id[t[1].mx[0]];!v[j]&&j;j=fa[j])
    135         {
    136             v[j]=1;
    137             add(1,l[j],l[j],inf);
    138             if(l[j]+1<r[j])add(1,l[j]+1,r[j]-1,a[j]);
    139             add(1,r[j],r[j],inf);
    140         }
    141     }
    142     printf("%lld
    ",ans);
    143 
    144     return 0;
    145 
    146 } 
    View Code

     这是不是树上费用流的弱化版?

  • 相关阅读:
    API学习
    某社区的常用免费图床 free image hosting websites,如何用Ruby与Perl启动浏览器, 打开指定网页
    Delphi7下SuperObject的JSON使用方法
    Delphi中使用ISuperObject解析Json数据
    Delphi 数据存储到oracle数据库TBLOB/TCLOB的方法 包括JSON串的解析
    Delphi7 JSON的读取和拼接
    SQL查看所有表大小的语句
    ora12541监听程序无法识别连接
    oracle新建用户类问题
    Delphi版本插值Lagrange
  • 原文地址:https://www.cnblogs.com/zyfzyf/p/4123876.html
Copyright © 2020-2023  润新知