注意到只有增加点/合并的操作。这些操作都可以用线段树完成,于是线段树合并一发就好了。注意乘积大小直接比较肯定会炸,取个对数即可。数据中存在重边。

#include<iostream>
#include<cstdio>
#include<cmath>
#include<cstdlib>
#include<cstring>
#include<algorithm>
using namespace std;
int read()
{
int x=,f=;char c=getchar();
while (c<''||c>'') {if (c=='-') f=-;c=getchar();}
while (c>=''&&c<='') x=(x<<)+(x<<)+(c^),c=getchar();
return x*f;
}
#define N 400010
#define inf 1000000000
int m,tot,fa[N],root[N],cnt;
int find(int x){return fa[x]==x?x:fa[x]=find(fa[x]);}
struct data{int l,r,s;double v;bool f;
}tree[N*];
void up(int k)
{
tree[k].s=tree[tree[k].l].s+tree[tree[k].r].s;
tree[k].v=tree[tree[k].l].v+tree[tree[k].r].v;
}
void down(int k)
{
tree[tree[k].l].f=tree[tree[k].r].f=;
tree[tree[k].l].s=tree[tree[k].r].s=;
tree[tree[k].l].v=tree[tree[k].r].v=;
tree[k].f=;
}
void ins(int &k,int l,int r,int x,int s,double y)
{
if (!k) k=++cnt;
tree[k].v+=y;tree[k].s+=s;
if (l==r) return;
if (tree[k].f) down(k);
int mid=l+r>>;
if (x<=mid) ins(tree[k].l,l,mid,x,s,y);
else ins(tree[k].r,mid+,r,x,s,y);
}
int merge(int x,int y,int l,int r)
{
if (!x||!y) return x|y;
tree[x].s+=tree[y].s,tree[x].v+=tree[y].v;
if (l<r)
{
if (tree[x].f) down(x);if (tree[y].f) down(y);
int mid=l+r>>;
tree[x].l=merge(tree[x].l,tree[y].l,l,mid);
tree[x].r=merge(tree[x].r,tree[y].r,mid+,r);
}
return x;
}
int modify(int k,int l,int r,int x,int y)
{
if (x>y||!k) return ;
if (l==x&&r==y)
{
int p=tree[k].s;
tree[k].s=,tree[k].v=,tree[k].f=;
return p;
}
if (tree[k].f) down(k);
int mid=l+r>>,ans;
if (y<=mid) ans=modify(tree[k].l,l,mid,x,y);
else if (x>mid) ans=modify(tree[k].r,mid+,r,x,y);
else ans=modify(tree[k].l,l,mid,x,mid)+modify(tree[k].r,mid+,r,mid+,y);
up(k);
return ans;
}
int query(int k,int l,int r,int x)
{
if (l==r) return l;
if (tree[k].f) down(k);
int mid=l+r>>;
if (tree[tree[k].l].s>=x) return query(tree[k].l,l,mid,x);
else return query(tree[k].r,mid+,r,x-tree[tree[k].l].s);
}
int main()
{
#ifndef ONLINE_JUDGE
freopen("bzoj4399.in","r",stdin);
freopen("bzoj4399.out","w",stdout);
const char LL[]="%I64d\n";
#else
const char LL[]="%lld\n";
#endif
m=read();
while (m--)
{
int op=read();
switch(op)
{
case :
{
fa[++tot]=tot;int x=read();
ins(root[tot],,inf,x,,log(x));
break;
}
case :
{
int x=find(read()),y=find(read());
if (x!=y) root[x]=merge(root[x],root[y],,inf);
fa[y]=x;
break;
}
case :
{
int p=find(read()),x=read();
int s=modify(root[p],,inf,,x-);
ins(root[p],,inf,x,s,s*log(x));
break;
}
case :
{
int p=find(read()),x=read();
int s=modify(root[p],,inf,x+,inf);
ins(root[p],,inf,x,s,s*log(x));
break;
}
case :
{
int p=find(read()),x=read();
printf("%d\n",query(root[p],,inf,x));
break;
}
case :
{
int x=find(read()),y=find(read());
printf("%d\n",tree[root[x]].v>tree[root[y]].v);
break;
}
case :
{
int x=find(read());
printf("%d\n",tree[root[x]].s);
break;
}
}
}
return ;
}

BZOJ4399 魔法少女LJJ(线段树合并)的更多相关文章

  1. BZOJ4399魔法少女LJJ——线段树合并+并查集

    题目描述 在森林中见过会动的树,在沙漠中见过会动的仙人掌过后,魔法少女LJJ已经觉得自己见过世界上的所有稀奇古怪的事情了LJJ感叹道“这里真是个迷人的绿色世界,空气清新.淡雅,到处散发着醉人的奶浆味: ...

  2. bzoj4399 魔法少女LJJ 线段树合并

    只看题面绝对做不出系列.... 注意到\(c \leqslant 7\),因此不会有删边操作(那样例删边干嘛) 注意到\(2, 5\)操作十分的有趣,启示我们拿线段树合并来做 操作\(7\)很好处理 ...

  3. bzoj4399 魔法少女LJJ 线段树合并+线段树二分+并查集

    题目传送门 https://lydsy.com/JudgeOnline/problem.php?id=4399 题解 毒瘤题 \(9\) 种操作还有支持动态图的连通性 仔细读题 $ c<=7$. ...

  4. 【BZOJ4399】魔法少女LJJ 线段树合并

    [BZOJ4399]魔法少女LJJ Description 在森林中见过会动的树,在沙漠中见过会动的仙人掌过后,魔法少女LJJ已经觉得自己见过世界上的所有稀奇古怪的事情了LJJ感叹道“这里真是个迷人的 ...

  5. BZOJ 4399: 魔法少女LJJ 线段树合并 + 对数

    Description 在森林中见过会动的树,在沙漠中见过会动的仙人掌过后,魔法少女LJJ已经觉得自己见过世界上的所有稀奇古怪的事情了LJJ感叹道“这里真是个迷人的绿色世界,空气清新.淡雅,到处散发着 ...

  6. BZOJ.4399.魔法少女LJJ(线段树合并)

    BZOJ 注意\(c\leq7\)→_→ 然后就是裸的权值线段树+线段树合并了. 对于取\(\max/\min\)操作可以直接区间修改清空超出范围的值,然后更新到对应位置上就行了(比如对\(v\)取\ ...

  7. 魔法少女 LJJ——线段树

    题目 [题目描述] 在森林中见过会动的树,在沙漠中见过会动的仙人掌过后,魔法少女 LJJ 已经觉得自己见过世界上的所有稀奇古怪的事情了. LJJ 感叹道“这里真是个迷人的绿色世界,空气清新.淡雅,到处 ...

  8. BZOJ 4399: 魔法少女LJJ(线段树)

    传送门 解题思路 出题人真会玩..操作\(2\)线段树合并,然后每棵线段树维护元素个数和.对于\(6\)这个询问,因为乘积太大,所以要用对数.时间复杂度\(O(nlogn)\) 代码 #include ...

  9. BZOJ4399 魔法少女LJJ【线段树合并】【并查集】

    Description 在森林中见过会动的树,在沙漠中见过会动的仙人掌过后,魔法少女LJJ已经觉得自己见过世界上的所有稀奇古怪的事情了 LJJ感叹道"这里真是个迷人的绿色世界,空气清新.淡雅 ...

随机推荐

  1. thinkphp5数据库导入Excel表格

    $data=$order_info; //$data 你要下载谁 就去查谁 // $data= Db::name('order_info') // ->field('consignee,tel, ...

  2. ajax提交时 富文本CKEDITOR 获取不到内容

    ckeditor数据向content(页面用以替换的编辑框)的同步 问题: 我们发现,在数据通过ajaxSubmit提交的过程中,并不能将最新的数据进行提交.换句话说,最新的数据无法被jQuery.f ...

  3. pyspider -- 禁止请求非200响应码抛异常

    在pyspider中若crawl()网址时出现非200的异常信息,会抛出一个异常. 可以在对应的回调函数上面通过@catch_status_code_error 进行修饰,这样就能不抛出异常正常进入回 ...

  4. 2019-04-10 python入门学习——教材和工具准备

    # 从决定学习编程语言到正式做出计划挤出空余时间,历经一年半,因工作原因及生活原因不断搁浅,从湖北到浙江再回湖北,暂时稳定在一家小公司,从日常加班中压缩时间学习,于此记录学习进度.学习问题,在此过程中 ...

  5. PHP通过copy()函数来复制一个文件

    PHP通过copy()函数来复制一个文件.用法如下: bool copy(string $source, string $dest) 其中$source是源文件的路径,$dest是目的文件的路径.函数 ...

  6. 存一些有用的CSS

    reset ;} table{} fieldset,img{} address,caption,cite,code,dfn,em,strong,th,var{font-style:normal;fon ...

  7. 解决灰色shader与mask冲突的方案

    Shader "Custom/Opaque" { Properties { [PerRendererData] _MainTex ("Sprite Texture&quo ...

  8. 不得不服!Python速度虽然慢,但是它工作效率很高!

    写在前面 让我们来讨论一个我最近一直在思考的问题:Python 的性能.顺便说一下,我是 Python 的忠实拥趸,我在各种情况下都会积极尝试使用 Python 来解决问题.大家对 Python 最大 ...

  9. 【java并发编程实战】第七章:取消与关闭

    停止线程的几种方式 一般的逻辑停止 public class ThreadInterruptTest { public static volatile boolean cancel = true; p ...

  10. 【page.js】配置及Page函数说明

    页面.js中的Page函数用来注册一个页面,指定页面的初始数据.生命周期回调.事件处理函数等. 语法:Page(Object)参数: Object json对象 Page({ /** * data * ...