淀粉质入门第一道 (现在个人认为spoj比bzoj要好_(:з」∠)_

关于点分治的话推荐去看一看漆子超的论文>>>这里这里<<<

之前一直试图入点分治坑, 但是因为种(bu)种(duan)原(tui)因(fei)也没有入...

结果经常碰到点分治的题目... 然后就各种弃疗...

不少点分治的题目有非常明显的特征... 通常是给一棵树, 然后问你满足xx条件的路径有多少条/是否存在/最大(小)权值之类的...

然后点分治的做法也不尽相同 大致能写出如下的伪代码(好吧还是用python高亮)

def solve(x):        # 处理以x为根的子树
vis[x]=1 # 把x标记为操作过(视为删掉)
findroot(x) # 找到以x为根的子树的重心
calc(x) # 统计过x的路径的答案
for i in son[x]: # 对于每个儿子
solve(i) # 递归处理答案

然后刚入门第一道就不能算是很裸的点分治_(:з」∠)_

几乎抄了黄学长的代码, 在此表示感谢..

<题目の传送门>

hzwer题解の传送门

题目大意:

给一棵树, 有\(m\)个点上有一个标记, 边有边权, 可正可负.

询问路径上带标记的点不超过\(k\)个的路径的最大权值是多少.

首先朴素的思路就是暴力嘛... 复杂度\(O(n^2)\)的.. 可能能拿30~40(但这是spoj所以并没有什么部分分..)

我们要考虑复杂度更好的做法.. 首先根据上面我们说过的特征, 可以看出这题应该可以用点分治做...

因为后面是递归处理的, 我们只需要考虑如何统计合法的过根节点的路径的答案就行了..


我们需要处理出\(dep[y]\)和\(dis[y]\)两个数组, 分别表示\(y\)到当前的根节点(以下的根节点均指当前子树的根节点, 因为原来的根节点处理过就删掉了)的路径上的带标记节点个数和路径权值和. 这个可以通过一遍dfs\(O(n)\)完成...

然后我们考虑有哪些路径会对答案产生影响...

假如我们要处理\(x\)的\(i\)个子树, 那么前\(i-1\)个子树中的点可以与这个子树中的点确定一条路径.

我们再用一遍\(O(n)\)的dfs处理出\(mx[t]\)这个数组, 表示从前\(i-1\)棵子树中到根节点的经过\(t\)个带标记节点的路径的最大长度..

那我们就可以得到:

\[ans=max\{mx[t]+dis[x]\} (dep[x]+t<=k)
\]

但是这个dep[x]是会变的, 所以我们可以把儿子按照dep排序一波再做, 就可以顺着推过去了, 据说这样的复杂度是\(O(n)\)级别的..

然后排序的话总共也就只是\(O(nlogn)\)级别的东西, 配合着点分治的复杂度, 最后就是\(O(nlogn)\)咯..

代码:

#include <cstdio>
#include <vector>
#include <algorithm>
using namespace std;
#define depth first
#define id second
const int N=202020;
inline int gn(int a=0,char c=0,int f=1){
for(;(c<48||c>57)&&c!='-';c=getchar());if(c=='-')c=getchar(),f=-1;
for(;c>47&&c<58;c=getchar()) a=a*10+c-'0'; return a*f;
}
struct edge{
int to,next,data;
}e[N<<1]; int v[N],tot,n,m,k,rt,size,ans;
void buildedge(int x,int y,int z){
e[++tot].to=y; e[tot].next=v[x]; v[x]=tot; e[tot].data=z;
e[++tot].to=x; e[tot].next=v[y]; v[y]=tot; e[tot].data=z;
}
int q[N],fa[N],son[N],sz[N],mx[N],tmp[N],dep[N],d[N],depmx;
bool vis[N],a[N];
void findrt(int x,int fa){
sz[x]=1; son[x]=0;
for(int i=v[x];i;i=e[i].next)
if(!vis[e[i].to]&&e[i].to!=fa){
findrt(e[i].to,x);
son[x]=max(son[x],sz[e[i].to]);
sz[x]+=sz[e[i].to];
}
son[x]=max(son[x],size-sz[x]);
if(son[x]<son[rt]) rt=x;
}
void calcdis(int x,int fa){
depmx=max(depmx,dep[x]);
for(int i=v[x];i;i=e[i].next)
if(!vis[e[i].to]&&e[i].to!=fa){
dep[e[i].to]=dep[x]+a[e[i].to];
d[e[i].to]=d[x]+e[i].data;
calcdis(e[i].to,x);
}
}
void calcmax(int x,int fa){
tmp[dep[x]]=max(tmp[dep[x]],d[x]);
for(int i=v[x];i;i=e[i].next)
if(!vis[e[i].to]&&e[i].to!=fa)
calcmax(e[i].to,x);
}
vector<pair<int,int> > vec;
void solve(int x){
vis[x]=1; vec.clear(); if(a[x]) --k;
for(int i=v[x];i;i=e[i].next)
if(!vis[e[i].to]){
depmx=0;
dep[e[i].to]=a[e[i].to];
d[e[i].to]=e[i].data;
calcdis(e[i].to,x);
vec.push_back(make_pair(depmx,e[i].to));
}
sort(vec.begin(),vec.end());
for(int i=0;i<vec.size();++i){
calcmax(vec[i].id,x);
int now=0;
if(i!=0)
for(int j=vec[i].depth;j>=0;--j){
while(now+j<k&&now<vec[i-1].depth)
++now,mx[now]=max(mx[now],mx[now-1]);
if(now+j<=k) ans=max(ans,mx[now]+tmp[j]);
}
if(i!=vec.size()-1)
for(int j=0;j<=vec[i].depth;++j)
mx[j]=max(mx[j],tmp[j]),tmp[j]=0;
else
for(int j=0;j<=vec[i].depth;++j){
if(j<=k) ans=max(ans,max(tmp[j],mx[j]));
tmp[j]=mx[j]=0;
}
}
if(a[x]) ++k;
for(int i=v[x];i;i=e[i].next)
if(!vis[e[i].to]){
rt=0; size=sz[e[i].to];
findrt(e[i].to,x);
solve(rt);
}
}
int main(){
n=gn(),k=gn(),m=gn();
for(int i=1;i<=m;++i) a[gn()]=1;
for(int i=1;i<n;++i){
int x=gn(),y=gn(),z=gn();
buildedge(x,y,z);
}
size=son[0]=n; findrt(1,0);
solve(rt);
printf("%d",ans);
}

【学术篇】SPOJ FTOUR2 点分治的更多相关文章

  1. 【学术篇】CF833B TheBakery 分治dp+主席树

    题目の传送门~ 题目大意: 将\(n\)个蛋糕分成恰好\(k\)份, 求每份中包含的蛋糕的种类数之和的最大值. 这题有两种做法. 第一种是线段树优化dp, 我还没有考虑. 另一种就是分治+主席树. 然 ...

  2. [spoj] FTOUR2 FREE TOUR II || 树分治

    原题 给出一颗有n个点的树,其中有M个点是拥挤的,请选出一条最多包含k个拥挤的点的路径使得经过的权值和最大. 正常树分治,每次处理路径,更新答案. 计算每棵子树的deep(本题以经过拥挤节点个数作为d ...

  3. SPOJ - FTOUR2 (点分治+树状数组)

    题目:https://vjudge.net/contest/307753#problem/I 题意:有一颗树,上面有白色黑色点,每个点上有一个权值,权值可以为负,现在我要求一条路径,权值和最大,这条路 ...

  4. 【学术篇】SPOJ GEN Text Generator AC自动机+矩阵快速幂

    还有5天省选才开始点字符串这棵技能树是不是太晚了点... ~题目の传送门~ AC自动机不想讲了QAQ.其实很久以前是学过然后打过板子的, 但也仅限于打过板子了~ 之前莫名其妙学了一个指针版的但是好像不 ...

  5. 【学术篇】bzoj3262 陌上花开. cdq分治入门

    花儿们已经很累了-- 无论是花形.颜色.还是气味, 都不是为了给人们摆出来欣赏的, 更不是为了当做出题的素材的, 她们并不想自己这些属性被没有生命的数字量化, 并不想和其它的花攀比, 并无意分出个三六 ...

  6. 【学术篇】SPOJ QTREE 树链剖分

    发现链剖这东西好久不写想一遍写对是有难度的.. 果然是熟能生巧吧.. WC的dalao们都回来了 然后就用WC的毒瘤题荼毒了我们一波, 本来想打个T1 44分暴力 然后好像是特判写挂了还是怎么的就只能 ...

  7. 【学术篇】SPOJ COT 树上主席树

    这是学完主席树去写的第二道题_(:з」∠)_ 之前用树上莫队水过了COT2... 其实COT也可以用树上莫队水过去不过好像复杂度要带个log还是怎么样可能会被卡常数.. 那就orz主席吧.... 写了 ...

  8. 【学术篇】一些水的不行的dp

    最近做了几道非常水非常水的dp...... 之后刷的一些水dp也会写在这里...... 此篇题目难度不递增!!! Emmmm....... 1.luogu1043数字游戏 以前看过这个题几遍,没做这个 ...

  9. SPOJ FTOUR2 - Free tour II

    Description 有些黑点,问你选择不超过 \(k\) 个黑点的路径,路径权值最大是多少. Sol 点分治. 这是qzc的论文题,不过我感觉他的翻译好强啊...我还是选择了自己去看题目... 点 ...

随机推荐

  1. javascript中var同时声明多个变量时的原理是什么?

    <script> function show(){ var a=b=c=d=5; } show(); alert(a);//弹a时报错(not defined),而b.c.d都能弹出5 & ...

  2. vps被封逃逸_v2+cloudflare+websocket+tls+nginx

    每逢重大节日,总有那么一大部分vps凉凉,以下为能正经正常使用vps,无奈之举,此法由于多层代理,夜间速度会有影响,白天感受不明显. 由于博客园内容审查,v2_ray 中间的 下划线为分隔符,相关链接 ...

  3. LeetCode Array Easy 217. Contains Duplicate

    Description Given an array of integers, find if the array contains any duplicates. Your function sho ...

  4. Spark使用Java读取mysql数据和保存数据到mysql

    原文引自:http://blog.csdn.net/fengzhimohan/article/details/78471952 项目应用需要利用Spark读取mysql数据进行数据分析,然后将分析结果 ...

  5. 导入C文件Xcode出现Could not build module 'Foundation'错误

    #ifdef __OBJC__ #import <Foundation/Foundation.h> #import "UIImageView+WebCache.h" # ...

  6. 笔记59 Spring+Hibernate整合(二)

    一.项目结构 二.创建表 数据库中只有一张表,stock,三个字段:stock_id.stock_code和stock_name. CREATE TABLE `stock` ( `STOCK_ID` ...

  7. 通信矩阵转DBC

    DBC的制作对于一些人来时比较陌生,熟悉的人做他感觉浪费时间(像我这样的),于是自己用PYTHON写了一个脚本,还挺好用的,只需要填写表格就好了,省出来大部分的时间. 分享下思路, 来看下DBC的文本 ...

  8. rest framework之视图组件

    一.APIView  APIView继承的是和django中CBV模式下的View类.View类中的dispatch方法通过反射对不同的请求方法执行不同的函数.而APIView不仅拥有这个特性,而且重 ...

  9. Spring Boot 2.0 常见问题总结(二)

    使用 IDEA 生成 POJO 实体类 a. 使用 idea 连接上需要操作的数据库. b. 选中要生成实体类的数据库表:右键 ---> Scripted Extensions ---> ...

  10. MySQL常用操作2

    MySQL常用操作2 判断函数 IF(expr, value1, value2)  --  如果表达式expr为true,则返回value1,否则返回value2 IFNULL(value1, val ...