题面

思路

点分治非常$naive$,不讲了,基本思路就是记录路径最小最大值.....然后没了

重点讲一下LCT的做法(好写不卡常)(点分一堆人被卡到飞起hhhh)

首先,这个路径限制由边限制决定,而树中的每条边都是割边

考虑一条边$i$,范围是$[l_i,r_i]$,那么当时间不在这个范围内的时候,这个边两边的点肯定不能跨过这条边有赚钱路径

那么,也就是说这一条边当且仅当时间在$[l_i,r_i]$范围内的时候生效

这样,我们可以考虑把边权范围限制变成一次加边和一次删边

我们把一条边根据加入删除的时间分成2条,并且把$2*(n-1)$条边按照时间排序

每次加入边的时候,统计这个边两边的联通块大小,乘起来加入答案

删边的时候就是把边删掉

这样子统计的话,我们容易发现,每条路径都只会被路径上加入最晚的那条边统计答案,不会有重复也不会有遗漏(不流失不蒸发

这样就做完了,比点分治好写,而且跑的快【雾】

Code

依然是只提供LCT做法(实际是博主并没有写点分做法【逃】)

#include<iostream>
#include<cstdio>
#include<cstring>
#include<algorithm>
#define ll long long
using namespace std;
inline int read(){
int re=0,flag=1;char ch=getchar();
while(!isdigit(ch)){
if(ch=='-') flag=-1;
ch=getchar();
}
while(isdigit(ch)) re=(re<<1)+(re<<3)+ch-'0',ch=getchar();
return re*flag;
}
int n,fa[200010],ch[200010][2],siz[200010],vir[200010],rev[200010];
inline void update(int cur){
siz[cur]=siz[ch[cur][0]]+siz[ch[cur][1]]+1+vir[cur];
}
inline bool nroot(int cur){return ((ch[fa[cur]][0]==cur)||(ch[fa[cur]][1]==cur));}
inline bool get(int cur){return ch[fa[cur]][1]==cur;}
inline void rotate(int cur){
int f=fa[cur],ff=fa[f],son=get(cur),nr=nroot(f);
ch[f][son]=ch[cur][son^1];
if(ch[f][son]) fa[ch[f][son]]=f;
ch[cur][son^1]=f;fa[f]=cur;
fa[cur]=ff;
if(nr) ch[ff][ch[ff][1]==f]=cur;
update(f);update(cur);
}
void pushrev(int x){
if(!x) return;
swap(ch[x][0],ch[x][1]);
rev[x]^=1;
}
void pushdown(int x){
if(rev[x]){
pushrev(ch[x][0]);
pushrev(ch[x][1]);
rev[x]=0;
}
}
void push(int x){
if(nroot(x)) push(fa[x]);
pushdown(x);
}
void splay(int x){
push(x);
for(int f;nroot(x);rotate(x)){
f=fa[x];
if(nroot(f))
rotate((get(x)==get(f))?f:x);
}
}
void access(int x){
for(int y=0;x;y=x,x=fa[x]){
splay(x);
vir[x]+=(siz[ch[x][1]]);
ch[x][1]=y;
vir[x]-=(siz[y]);
update(x);
}
}
void mroot(int x){
access(x);splay(x);pushrev(x);
}
void cut(int x,int y){
mroot(x);access(y);splay(y);
ch[y][0]=0;fa[x]=0;update(y);
}
ll link(int x,int y){
mroot(x);mroot(y);
ll re=(ll)siz[x]*(ll)siz[y];
fa[y]=x;vir[x]+=(siz[y]);update(x);
return re;
}
struct edge{
int u,v,w,f;
}a[400010];
inline bool cmp(edge l,edge r){
if(l.w==r.w) return l.f<r.f;
return l.w<r.w;
}
int main(){
n=read();int i,t1,t2,t3,t4;ll ans=0;
for(i=1;i<=n;i++) siz[i]=1,vir[i]=0,fa[i]=ch[i][0]=ch[i][1]=rev[i]=0;
for(i=1;i<n;i++){
t1=read();t2=read();t3=read();t4=read();
a[i]=(edge){t1,t2,t3,0};
a[n+i-1]=(edge){t1,t2,t4,1};
}
sort(a+1,a+(n<<1)-1,cmp);
for(i=1;i<=((n-1)<<1);i++){
if(!a[i].f) ans+=link(a[i].u,a[i].v);
else cut(a[i].u,a[i].v);
}
printf("%lld\n",ans);
}

股神小D [点分治 or LCT]的更多相关文章

  1. 股神小L 2016Vijos省选集训 day1

    股神小L (stock.c/pas/cpp)============================ 小L厌倦了算法竞赛,希望到股市里一展身手.他凭借自己还行的计算机功底和可以的智商,成功建立一个模型 ...

  2. (2016北京集训十四)【xsy1556】股神小D - LCT

    题解: 题解居然是LCT……受教了 把所有区间按照端点排序,动态维护目前有重叠的区间,用LCT维护即可. 代码: #include<algorithm> #include<iostr ...

  3. 股神小D

    题目大意: 给定一棵树,每一条边有$L,R$两种权值,求有多少条路径满足$\max(L)\leq\min(R)$. 解法$1-$点分治$+$二维数点 统计树上的路径应首先想到点分治,我们很显然可以搜出 ...

  4. 2016vijos 1-2 股神小L(堆)

    维护前i天的最优解,那么在后面可能会对前面几天的买卖情况进行调整 如果前面买入,买入的这个在后面一定不会卖出 如果前面卖出,卖出的这个可能会在后面变成买入,因为买这个,卖后面的会获得更多的收益 用一个 ...

  5. [2016北京集训试题14]股神小D-[LCT]

    Description Solution 将(u,v,l,r)换为(1,u,v,l)和(2,u,v,r).进行排序(第4个数为第一关键字,第1个数为第二关键字).用LCT维护联通块的合并和断开.(维护 ...

  6. 股神小L

    题解 贪心 若当前手中还持有股,则一定会卖出去. 否则,考虑之前卖出的最便宜的股,若售价比当前的股高,就买下这个股,否则我们就把之前卖出的最便宜的股改为买入,这样一定会有股,然后再把这个股卖出即可. ...

  7. 2016北京集训测试赛(十四)Problem B: 股神小D

    Solution 正解是一个\(\log\)的link-cut tree. 将一条边拆成两个事件, 按照事件排序, link-cut tree维护联通块大小即可. link-cut tree维护子树大 ...

  8. 股神小L [贪心]

    题面 思路 股票题肯定是贪心或者$dp$啊 这个题比较$naive$,可以看出来你这里买股票的过程一定是能不买就不买,能卖就拣最贵的日子卖,而且时间不能倒流(废话= =||) 所以我们按照时间从前往后 ...

  9. 2016北京集训测试赛(十四)Problem A: 股神小L

    Solution 考虑怎么卖最赚钱: 肯定是只卖不买啊(笑) 虽然说上面的想法很扯淡, 但它确实能给我们提供一种思路, 我们能不买就不买; 要买的时候就买最便宜的. 我们用一个优先队列来维护股票的价格 ...

随机推荐

  1. xcode怎样分析检测内存泄露(iOS)

    虽然iOS 5.0版本之后加入了ARC机制,由于相互引用关系比较复杂时,内存泄露还是可能存在.所以了解原理很重要. 这里讲述在没有ARC的情况下,如何使用Instruments来查找程序中的内存泄露, ...

  2. mybatis的坑——不报错,就是不能committing,数据存不进数据库

    测试的时候会报空指针异常,在项目跑的时候会停止执行程序,不会出现异常. 经过一星期的排查与测试,最终找到错误,把mapper文件的映射属性名写错了. property属性名要与接收类的属性名保持一致. ...

  3. LeetCode961 重复 N 次的元素

    问题: 重复 N 次的元素 在大小为 2N 的数组 A 中有 N+1 个不同的元素,其中有一个元素重复了 N 次. 返回重复了 N 次的那个元素. 示例 1: 输入:[1,2,3,3] 输出:3 示例 ...

  4. 【PHP】nl2br转化输出input框的换行

    在input或者textarea框中输入的换行符保存到数据库是/n,如果直接输出到前端的话是不会有换行的,所以要用到nl2br转化 nl2br($test);

  5. 通信服务器哈希Socket查找(Delphi)

    在Socket通信服务器的开发中,我们经常会需要Socket与某个结构体指针进行绑定.当连接量很大时,意味着需要个高效的查找方法 Delphi中提供了哈希算法类,以此类为基础,修改出Socket专用M ...

  6. python中函数的不定长参数

    例1: #定义一个含有不定长参数的函数,本例第三个参数*args def sum_nums(a,b,*args): print('_'*30) print(a) print(b) print(args ...

  7. B1076 Wifi密码 (15分)

    B1076 Wifi密码 (15分) 下面是微博上流传的一张照片:"各位亲爱的同学们,鉴于大家有时需要使用 wifi,又怕耽误亲们的学习,现将 wifi 密码设置为下列数学题答案:A-1:B ...

  8. 使用Windows Live Writer写文章时不要用360清除垃圾

    ref:http://www.zhengsiwei.com/write-an-article-to-use-windows-live-writer-dont-use-360-to-remove-rub ...

  9. HTML介绍和head标签-01

    主要内容 web标准 浏览器介绍 开发工具介绍 HTML介绍 HTML颜色介绍 HTML规范 HTML结构详解 一.web标准 web准备介绍: w3c:万维网联盟组织,用来制定web标准的机构(组织 ...

  10. Android 图片放错位置会拉伸变形

    今天做了一个很小的需求,然后需要图片,我给ui要图片.直接给了我三套,还命名 x . xx. 2k 真的一开始都不知道.没有玩过这么正规的.我就用了一张,放到了hdpi下面. 后来同事帮我才知道, 图 ...