Description

浩浩荡荡的cg大军发现了一座矿产资源极其丰富的城市,他们打算在这座城市实施新的采矿战略。这个城市可以看成一棵有n个节点的有根树,我们把每个节点用1到n的整数编号。为了方便起见,对于任何一个非根节点v,它任何一个祖先的编号都严格小于v。树上的每个节点表示一个矿点,每条边表示一条街道。作为cg大军的一个小队长,你拥有m个部下。你有一张二维的动态信息表,用Ti,j表示第i行第j列的数据。当你被允许开采某个区域时,你可以将你的部下分配至各个矿点。在第i个矿点安排j个人可以获得Ti,j单位的矿产。允许开采的区域是这样描述的:给你一对矿点(u,v),保证v是u的祖先(这里定义祖先包括u本身);u为你控制的区域,可以在以u为根的子树上任意分配部下;u到v的简单路径(不包括u但包括v,若u=v则包括u)为探险路径,在该路径上你可以选择至多一个矿点安排部下。你这次开采的收益为安排有部下的矿点的收益之和。

Solution

对于子树维护一个背包数组, \(f[i]\) 表示取 \(i\) 个的最大收益,链上维护一个 \(max\)

把子树内的合并,链上的不合并,分别维护即可

线段树查询子树,树链剖分查询一下路径 \((x,y)\) 上的点即可

#include<bits/stdc++.h>
#define ls (o<<1)
#define rs (o<<1|1)
using namespace std;
template<class T>void gi(T &x){
int f;char c;
for(f=1,c=getchar();c<'0'||c>'9';c=getchar())if(c=='-')f=-1;
for(x=0;c<='9'&&c>='0';c=getchar())x=x*10+(c&15);x*=f;
}
typedef long long ll;
const int N=20010,M=55;
int n,m,A,B,Q,fa[N],head[N],nxt[N],to[N],num=0,son[N],dep[N];
int sz[N],L[N],R[N],ID=0,top[N],b[N],X=1<<16,Y=(1ll<<31)-1;
struct data{ll f[M];
inline void init(){memset(f,0,sizeof(f));}
}tr[N*4],te[N*4],E,a[N],t0;
inline data operator +(data p,data q){
for(int i=0;i<=m;i++)p.f[i]=max(p.f[i],q.f[i]);
return p;
}
inline data operator *(data p,data q){
data ret;ret.init();
for(int i=0;i<=m;i++)
for(int j=0;i+j<=m;j++)ret.f[i+j]=max(ret.f[i+j],p.f[i]+q.f[j]);
return ret;
}
inline int getint(){
A=((A^B)+B/X+B*X)&Y;
B=((A^B)+A/X+A*X)&Y;
return (A^B)%Q;
}
inline void get(){
for(int i=1;i<=m;i++)E.f[i]=getint();
sort(E.f+1,E.f+m+1);
}
inline void link(int x,int y){nxt[++num]=head[x];to[num]=y;head[x]=num;}
inline void dfs1(int x){
sz[x]=1;
for(int i=head[x],u;i;i=nxt[i]){
if((u=to[i])==fa[x])continue;
dep[u]=dep[x]+1;dfs1(u);sz[x]+=sz[u];
if(sz[u]>sz[son[x]])son[x]=u;
}
}
inline void dfs2(int x,int tp){
b[L[x]=++ID]=x;top[x]=tp;
if(son[x])dfs2(son[x],tp);
for(int i=head[x];i;i=nxt[i])
if(to[i]!=fa[x] && to[i]!=son[x])dfs2(to[i],to[i]);
R[x]=ID;
}
inline void upd(int o){tr[o]=tr[ls]+tr[rs],te[o]=te[ls]*te[rs];}
inline void build(int l,int r,int o){
if(l==r){tr[o]=te[o]=a[b[l]];return ;}
int mid=(l+r)>>1;
build(l,mid,ls);build(mid+1,r,rs);
upd(o);
}
inline void mdf(int l,int r,int o,int sa){
if(l==r){tr[o]=te[o]=E;return ;}
int mid=(l+r)>>1;
if(sa<=mid)mdf(l,mid,ls,sa);
else mdf(mid+1,r,rs,sa);
upd(o);
}
inline data qr(int l,int r,int o,int sa,int se){
if(sa<=l && r<=se)return tr[o];
int mid=(l+r)>>1;
if(se<=mid)return qr(l,mid,ls,sa,se);
if(sa>mid)return qr(mid+1,r,rs,sa,se);
return qr(l,mid,ls,sa,mid)+qr(mid+1,r,rs,mid+1,se);
}
inline data qe(int l,int r,int o,int sa,int se){
if(sa<=l && r<=se)return te[o];
int mid=(l+r)>>1;
if(se<=mid)return qe(l,mid,ls,sa,se);
if(sa>mid)return qe(mid+1,r,rs,sa,se);
return qe(l,mid,ls,sa,mid)*qe(mid+1,r,rs,mid+1,se);
}
inline data solve(int x,int y){
data ret;ret.init();
if(x==y)return ret;
x=fa[x];
while(top[x]!=top[y]){
if(dep[top[x]]<dep[top[y]])swap(x,y);
ret=ret+qr(1,n,1,L[top[x]],L[x]);
x=fa[top[x]];
}
if(dep[x]>dep[y])swap(x,y);
ret=ret+qr(1,n,1,L[x],L[y]);
return ret;
}
int main(){
freopen("pp.in","r",stdin);
freopen("pp.out","w",stdout);
cin>>n>>m>>A>>B>>Q;
for(int i=2;i<=n;i++)gi(fa[i]),link(fa[i],i);
dfs1(1);dfs2(1,1);
for(int i=1;i<=n;i++)get(),a[i]=E;
build(1,n,1);
int C,op,x,y;
cin>>C;
while(C--){
gi(op);gi(x);
if(op==0)get(),mdf(1,n,1,L[x]);
else{
gi(y);
t0=qe(1,n,1,L[x],R[x])*solve(x,y);
printf("%lld\n",t0.f[m]);
}
}
return 0;
}

bzoj 2164: 采矿的更多相关文章

  1. bzoj AC倒序

    Search GO 说明:输入题号直接进入相应题目,如需搜索含数字的题目,请在关键词前加单引号 Problem ID Title Source AC Submit Y 1000 A+B Problem ...

  2. 树形dp专题总结

    树形dp专题总结 大力dp的练习与晋升 原题均可以在网址上找到 技巧总结 1.换根大法 2.状态定义应只考虑考虑影响的关系 3.数据结构与dp的合理结合(T11) 4.抽直径解决求最长链的许多类问题( ...

  3. BZOJ 2127: happiness [最小割]

    2127: happiness Time Limit: 51 Sec  Memory Limit: 259 MBSubmit: 1815  Solved: 878[Submit][Status][Di ...

  4. BZOJ 3275: Number

    3275: Number Time Limit: 10 Sec  Memory Limit: 128 MBSubmit: 874  Solved: 371[Submit][Status][Discus ...

  5. BZOJ 2879: [Noi2012]美食节

    2879: [Noi2012]美食节 Time Limit: 10 Sec  Memory Limit: 512 MBSubmit: 1834  Solved: 969[Submit][Status] ...

  6. bzoj 4610 Ceiling Functi

    bzoj 4610 Ceiling Functi Description bzoj上的描述有问题 给出\(n\)个长度为\(k\)的数列,将每个数列构成一个二叉搜索树,问有多少颗形态不同的树. Inp ...

  7. BZOJ 题目整理

    bzoj 500题纪念 总结一发题目吧,挑几道题整理一下,(方便拖板子) 1039:每条线段与前一条线段之间的长度的比例和夹角不会因平移.旋转.放缩而改变,所以将每条轨迹改为比例和夹角的序列,复制一份 ...

  8. 【sdoi2013】森林 BZOJ 3123

    Input 第一行包含一个正整数testcase,表示当前测试数据的测试点编号.保证1≤testcase≤20. 第二行包含三个整数N,M,T,分别表示节点数.初始边数.操作数.第三行包含N个非负整数 ...

  9. 【清华集训】楼房重建 BZOJ 2957

    Description 小A的楼房外有一大片施工工地,工地上有N栋待建的楼房.每天,这片工地上的房子拆了又建.建了又拆.他经常无聊地看着窗外发呆,数自己能够看到多少栋房子. 为了简化问题,我们考虑这些 ...

随机推荐

  1. python 批量创建文件

    # coding:utf8 import os path = "D:/Python_mkfile" os.chdir(path)#切换到该目录 ysyl = u"验收文件 ...

  2. repo搭建

    [root@op-yum01]# cat /home/work/yumdata/rsync-reposync.sh #!/bin/bash #Purpose: Sync centos7 repos v ...

  3. OCP 12c最新考试原题及答案(071-3)

    3.(4-10) choose the best answer:The user SCOTT who is the owner of ORDERS and ORDER_ITEMS tables iss ...

  4. java执行命令行命令

    package javai; import java.io.BufferedReader; import java.io.InputStreamReader; public class IOTest ...

  5. pop控制器

    1.寻找指定的控制器MineViewControllerclass UIViewController *mineVC = nil; for (UIViewController * controller ...

  6. eclipse项目目录展示结构设置

    我因为前后端都搞过, 解除过很多的开发IDE,说真的,很多的项目目录结构都是一级一级分开,然后我可以通过展开等操作来查看文件等资源信息,结果呢?java的开发IDE eclipse默认的项目目录展示简 ...

  7. 对EM算法的理解

    EM算法中要寻找的参数θ,与K-means聚类中的质心是对应的,在高斯混合模型中确定了θ,便可为样本进行类别的划分,属于哪个高斯分布的概率大就是哪一类,而这一点与K-means中的质心一样,质心确定了 ...

  8. Java非静态代码块和静态代码块

    类中存在两种特殊的代码块,即非静态代码块和静态代码块,前者是直接由 { } 括起来的代码,而后者是由 static{ } 括起来的代码. 非静态代码块在类初始化创建实例时,将会被提取到类的构造器中执行 ...

  9. 使用pageHelper遇到的问题

    在做SSM整合的时候,遇到一个小问题,在我使用pageHelper的时候,分页的效果总是无法正确显示,卡了我几个小时,现在来说一下我的问题.  1.首先导入pageHelper的包: <!--引 ...

  10. [LnOI2019]加特林轮盘赌

    Luogu5249 轮流开枪打一个环上的人 , 每次\(p\)的概率打死 , \(p\)始终相同 , 从第\(1\)个人开始 , 求第\(k\)个人成为唯一幸存者的概率 \(19.3.30\) 官方题 ...