bzoj3545/bzoj3551 [ONTAK2010]Peaks/Peaks加强版

传送门:bzoj  bzoj

wdnmd为什么加强版不是权限题原题却是啊

3545: [ONTAK2010]Peaks

Time Limit: 10 Sec  Memory Limit: 128 MB
[Submit][Status][Discuss]

Description

在Bytemountains有N座山峰,每座山峰有他的高度h_i。有些山峰之间有双向道路相连,共M条路径,每条路径有一个困难值,这个值越大表示越难走,现在有Q组询问,每组询问询问从点v开始只经过困难值小于等于x的路径所能到达的山峰中第k高的山峰,如果无解输出-1。

Input

第一行三个数N,M,Q。
第二行N个数,第i个数为h_i
接下来M行,每行3个数a b c,表示从a到b有一条困难值为c的双向路径。
接下来Q行,每行三个数v x k,表示一组询问。

Output

对于每组询问,输出一个整数表示答案。

Sample Input

10 11 4
1 2 3 4 5 6 7 8 9 10
1 4 4
2 5 3
9 8 2
7 8 10
7 1 4
6 7 1
6 4 8
2 1 5
10 8 10
3 4 7
3 4 6
1 5 2
1 5 6
1 5 8
8 9 2

Sample Output

6
1
-1
8

HINT

【数据范围】

N<=10^5, M,Q<=5*10^5,h_i,c,x<=10^9。



果然还是太年轻了居然被这种水平的题吊打。。。

简短思路:

首先来一次kruskal

很明显不在树上的边都用不上

然后这时候就出现了kruskal重构树

随便挂个讲得好的博客

拼出来重构树之后用线段树合并或是主席树都行

以下通用代码(只差一排注释)

  1 #include<cstdio>
  2 #include<algorithm>
  3 #include<cstring>
  4 using namespace std;
  5 const int N=200011,inf=0x7f7f7f7f,M=500011;
  6 template<typename TP>inline void read(TP &kk)
  7 {
  8     TP ret=0,f=1;char ch=getchar();
  9     while(ch<‘0‘||ch>‘9‘){if(ch==‘-‘)f=-1;ch=getchar();}
 10     while(ch>=‘0‘&&ch<=‘9‘){ret=ret*10+ch-‘0‘;ch=getchar();}
 11     kk=ret*f;
 12 }
 13 int n,m,Q;
 14 struct shino
 15 {
 16     int x,y,w;
 17     bool operator < (const shino &a)const
 18     {return w<a.w;}
 19 }sl[M];
 20 int snr;
 21 #define lson(x) (son[x][0])
 22 #define rson(x) (son[x][1])
 23 struct sgt
 24 {
 25     int c[N*36],son[N*36][2],cnt;
 26     void ins(const int x,int &px,int pl,int pr)
 27     {
 28         if(!px) px=++cnt;
 29         c[px]++;
 30         if(pl==pr) return;
 31         int mi=pl+pr>>1;
 32         if(x<=mi) ins(x,lson(px),pl,mi);
 33         else ins(x,rson(px),mi+1,pr);
 34     }
 35     int merge(const int px,const int py)
 36     {
 37         if(!px||!py) return px+py;
 38         int pz=++cnt;
 39         c[pz]=c[px]+c[py];
 40         lson(pz)=merge(lson(px),lson(py));
 41         rson(pz)=merge(rson(px),rson(py));
 42         return pz;
 43     }
 44     int query(int k,const int px,int pl,int pr)
 45     {
 46         if(pl==pr) return pl;
 47         int mi=pl+pr>>1;
 48         if(k<=c[lson(px)]) return query(k,lson(px),pl,mi);
 49         else return query(k-c[lson(px)],rson(px),mi+1,pr);
 50     }
 51 }tr;
 52 int rt[N];
 53 int h[N];
 54 int f[N],fa[N][20],val[N],son[N][2];
 55 int find(int x)
 56 {
 57     if(f[x]!=f[f[x]]) return f[x]=find(f[x]);
 58     return f[x];
 59 }
 60 void kksk()//k,k(ru)sk(al)... 无端玩梗的rkk是屑
 61 {
 62     snr=n,val[0]=inf;
 63     for(int i=1;i<=m;i++)
 64     {
 65         int x=find(sl[i].x),y=find(sl[i].y);
 66         if(x==y) continue;
 67         f[x]=f[y]=fa[x][0]=fa[y][0]=++snr;
 68         val[snr]=sl[i].w;
 69         son[snr][0]=x,son[snr][1]=y;
 70     }
 71 }
 72
 73 int saki[N];
 74 int main()
 75 {
 76     read(n),read(m),read(Q);
 77     for(int i=1;i<=n;i++)
 78         read(sl[i].w),sl[i].x=i;
 79     sort(sl+1,sl+1+n);
 80     for(int i=1;i<=n;i++)
 81     {
 82         if(sl[i].w!=sl[i-1].w) saki[++snr]=sl[i].w;
 83         h[sl[i].x]=snr;
 84     }
 85     for(int i=1;i<=m;i++)
 86         read(sl[i].x),read(sl[i].y),read(sl[i].w);
 87     sort(sl+1,sl+1+m);
 88     for(int i=1;i<=n*2;i++) f[i]=i;
 89     kksk();
 90     for(int i=1;i<=19;i++)
 91         for(int x=1;x<=snr;x++)
 92             fa[x][i]=fa[fa[x][i-1]][i-1];
 93     for(int i=1;i<=n;i++) tr.ins(h[i],rt[i],1,n);
 94     for(int i=n+1;i<=n*2;i++) rt[i]=tr.merge(rt[lson(i)],rt[rson(i)]);
 95     int lans=0,xi,vi,ki;
 96     while(Q--)
 97     {
 98         read(xi),read(vi),read(ki);
 99         xi^=lans,vi^=lans,ki^=lans;//前后就差个这行
100         for(int i=19;i>=0;i--)
101         {
102             if(val[fa[xi][i]]<=vi) xi=fa[xi][i];
103         }
104         if(tr.c[rt[xi]]<ki){puts("-1");lans=0;}
105         else printf("%d\n",lans=saki[tr.query(tr.c[rt[xi]]-ki+1,rt[xi],1,n)]);
106     }
107     return 0;
108 }

原文地址:https://www.cnblogs.com/rikurika/p/11332801.html

时间: 2024-10-05 23:27:08

bzoj3545/bzoj3551 [ONTAK2010]Peaks/Peaks加强版的相关文章

【bzoj3545】[ONTAK2010]Peaks 线段树合并

[bzoj3545][ONTAK2010]Peaks 2014年8月26日3,1512 Description 在Bytemountains有N座山峰,每座山峰有他的高度h_i.有些山峰之间有双向道路相连,共M条路径,每条路径有一个困难值,这个值越大表示越难走,现在有Q组询问,每组询问询问从点v开始只经过困难值小于等于x的路径所能到达的山峰中第k高的山峰,如果无解输出-1. Input 第一行三个数N,M,Q.第二行N个数,第i个数为h_i接下来M行,每行3个数a b c,表示从a到b有一条困难

bzoj3545 [ONTAK2010]Peaks、bzoj3551 [ONTAK2010]Peaks加强版

题目描述: bzoj3545,luogu bzoj3551 题解: 重构树+线段树合并. 可以算是板子了吧. 代码(强制在线): #include<cstdio> #include<cstring> #include<algorithm> using namespace std; const int N = 100050; const int M = 5*N; template<typename T> inline void read(T&x) {

bzoj3551 [ONTAK2010]Peaks加强版

Description //[题目描述]同3545 在Bytemountains有N座山峰,每座山峰有他的高度h_i.有些山峰之间有双向道路相连,共M条路径,每条路径有一个困难值,这个值越大表示越难走,现在有Q组询问,每组询问询问从点v开始只经过困难值小于等于x的路径所能到达的山峰中第k高的山峰,如果无解输出-1. Input 第一行三个数N,M,Q. 第二行N个数,第i个数为h_i 接下来M行,每行3个数a b c,表示从a到b有一条困难值为c的双向路径. 接下来Q行,每行三个数v x k,表

bzoj3545 &amp;&amp; bzoj3551 Peaks(离线版&amp;&amp;在线版)

题目给n点m边的无向图,有点权和边权 每次询问求点v在经过路径上的边都不超过w的情况下,能到达的第k大的点的权值 首先离线版比较容易想到,属于我现在能码出来的最难的码农题之一吧T T 这道题思路是这样的 1.对于边权的限制条件,可以先想到做一棵最小生成树 2.对于第k大这种询问,可以建权值线段树,但是山的高度太大到1e9,所以我们还要先离散化到1e6的水平才能用线段树 3.显然不能对每个询问w都建线段树,因此要用到主席树.具体做法是将询问和边权都排序(详情看代码),给每个点建一棵线段树,然后边建

[您有新的未分配科技点][BZOJ3545&amp;BZOJ3551]克鲁斯卡尔重构树

这次我们来搞一个很新奇的知识点:克鲁斯卡尔重构树.它也是一种图,是克鲁斯卡尔算法求最小生成树的升级版首先看下面一个问题:BZOJ3545 Peaks. 在Bytemountains有N座山峰,每座山峰有他的高度h_i.有些山峰之间有双向道路相连,共M条路径,每条路径有一个困难值,这个值越大表示越难走. 现在有Q组询问,每组询问询问从点v开始只经过困难值小于等于x的路径所能到达的山峰中第k高的山峰,如果无解输出-1.N<=1e5,M,Q<=5*1e5 上面这个题没有要求在线,因此我们可以离线构造

[您有新的未分配科技点]可,可,可持久化!?------可持久化线段树普及版讲解

最近跑来打数据结构,于是我决定搞一发可持久化,然后发现--一发不可收啊-- 对于可持久化数据结构,其最大的特征是"历史版本查询",即可以回到某一次修改之前的状态,并继续操作:而这种"历史版本查询"会衍生出其他一些强大的操作. 今天,我们主要讲解可持久化线段树.其实,它的另外一个名字"主席树"似乎更加为人所知(主席%%%). 主席树与普通的线段树相比,多出来的操作是在修改时复制修改的一条链,这个操作的过程大概长下面这样. 至于为什么要这样做-- 对

大神刷题表

9月27日 后缀数组:[wikioi3160]最长公共子串 dp:NOIP2001统计单词个数 后缀自动机:[spoj1812]Longest Common Substring II [wikioi3160]最长公共子串 [spoj7258]Lexicographical Substring Search 扫描线+set:[poj2932]Coneology 扫描线+set+树上删边游戏:[FJOI2013]圆形游戏 结论:[bzoj3706][FJ2014集训]反色刷 最小环:[poj1734

MATLAB图形界面设计(下)

文章参考Blue Mountain https://www.cnblogs.com/BlueMountain-HaggenDazs/p/4307777.html 一.菜单设计 1.建立菜单项 (1)建立一级菜单的函数调用: 一级菜单句柄=uimenu(图形窗口句柄,属性名1,属性值1,属性名2,属性值2,--); %建立一级菜单需给出图形窗口的句柄值. %如果省略句柄值,MATLAB就在当前图形窗口中建立这个菜单项. %如果当前没有图形窗口,则自动打开一个图形窗口. (2)建立子菜单项的函数调用

Octave 常用命令

GNU Octave 官方文档 GNU Octave Documentation(Online) GNU Octave Documentation(PDF) 安装额外的包 Installing and Removing Packages Octave Forge % 卸载包 pkg uninstall io statistics % 从 Octave Forge 仓库直接安装包 pkg install -forge io statistics % 从本地文件安装包 pkg install io.