题意

题目描述

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

输入输出格式

输入格式:

第一行三个数NNN,MMM,QQQ。
第二行NNN个数,第iii个数为hih_ihi​
接下来MMM行,每行333个数a,b,ca,b,ca,b,c,表示从aaa到bbb有一条困难值为ccc的双向路径。
接下来QQQ行,每行三个数v,x,kv,x,kv,x,k,表示一组询问。

输出格式:

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

输入输出样例

输入样例#1:
复制

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
输出样例#1:
复制

6
1
-1
8

说明

数据范围

N≤105,0≤M,Q≤5×105,hi,c,x≤109N \le 10^5, 0 \le M,Q \le 5\times 10^5,h_i,c,x \le 10^9N≤105,0≤M,Q≤5×105,hi​,c,x≤109。

分析

参照自为风月马前卒的题解。

首先由于给出的限制条件是<=x,因此我们在最小生成树上走一定是最优的。

考虑把Kruskal重构树建出来,重构树上每个新的节点代表的是边权,同时用倍增数组维护出向上跳2^i步后能走到的最大值

这样,该节点的整个子树内的节点都是可以走到的。

用dfs序+主席树维护出每个节点内H的值,直接查第K大即可

需要注意的是,对于不在原树内的节点,H要设的非常小,或者不插入,以免对答案产生影响

同时H需要离散化

时间复杂度\(O(n \log n)\)

代码

拒绝思考MLE的问题。

#include<bits/stdc++.h>
#define rg register
#define il inline
#define co const
template<class T>il T read(){
rg T data=0,w=1;
rg char ch=getchar();
while(!isdigit(ch)){
if(ch=='-') w=-1;
ch=getchar();
}
while(isdigit(ch))
data=data*10+ch-'0',ch=getchar();
return data*w;
}
template<class T>il T read(rg T&x){
return x=read<T>();
}
typedef long long ll;
using namespace std; co int MAXN=5e5+1;
int N,M,Q,H[MAXN],date[MAXN],tot,num;
struct Edge{
int u,v,w;
bool operator<(co Edge&rhs)co {return w<rhs.w;}
}E[MAXN];
int fa[MAXN],fd[MAXN][22],dis[MAXN][22];
int find(int x) {return fa[x]==x?x:fa[x]=find(fa[x]);}
vector<int> v[MAXN];
void Build() {
for(int i = 1; i <= (N << 1); i++) fa[i] = i;
sort(E + 1, E + num + 1);
for(int i = 1; i <= num; i++) {
int x = E[i].u, y = E[i].v, w = E[i].w;
int fx = find(x), fy = find(y);
if(fx == fy) continue;
tot++;
fa[fx] = tot; fa[fy] = tot;
v[fx].push_back(tot); v[fy].push_back(tot);
v[tot].push_back(fx); v[tot].push_back(fy);
dis[fx][0] = w; dis[fy][0] = w;
fd[fx][0] = tot; fd[fy][0] = tot;
if(tot == 2 * N - 1) break;
}
}
int ls[MAXN * 30], rs[MAXN * 30], Tsiz[MAXN * 30], root[MAXN], cnt, siz[MAXN], dfn[MAXN], tra[MAXN];
void dfs(int x, int fa) {
dfn[x] = ++cnt; tra[dfn[x]] = x; siz[x] = 1;
for(int i = 0; i < v[x].size(); i++) {
int to = v[x][i];
if(to == fa) continue;
dfs(to, x);
siz[x] += siz[to];
}
}
void update(int k) {
Tsiz[k] = Tsiz[ls[k]] + Tsiz[rs[k]];
}
void Insert(int &k, int p, int val, int l, int r) {
k = ++cnt;
ls[k] = ls[p]; rs[k] = rs[p]; Tsiz[k] = Tsiz[p];
if(val == -1) return ;
Tsiz[k]++;
if(l == r) return ;
int mid = l + r >> 1;
if(val <= mid) Insert(ls[k], ls[p], val, l, mid);
else Insert(rs[k], rs[p], val, mid + 1, r);
update(k);
}
void MakeTree() {
cnt = 0;
for(int i = 1; i <= tot; i++)
Insert(root[i], root[i - 1], H[tra[i]], 1, N);
}
void Jump() {
for(int j = 1; j <= 21; j++) {
for(int i = 1; i <= tot; i++) {
fd[i][j] = fd[fd[i][j - 1]][j - 1];
dis[i][j] = max(dis[fd[i][j - 1]][j - 1], dis[i][j - 1]);
}
}
}
int Get(int x, int val) {
for(int i = 21; i >= 0; i--)
if(dis[x][i] <= val && fd[x][i] != 0)
x = fd[x][i];
return x;
}
int Query(int lt, int rt, int k, int l, int r) {
int used = Tsiz[rs[rt]] - Tsiz[rs[lt]];
if(l == r) {
if(Tsiz[rt] - Tsiz[lt] < k) return -1;
else return l;
}
int mid = l + r >> 1;
if(k <= used) return Query(rs[lt], rs[rt], k, mid + 1, r);
else return Query(ls[lt], ls[rt], k - used, l, mid);
}
int main(){
// freopen(".in","r",stdin),freopen(".out","w",stdout);
tot=read(N),read(M),read(Q);
memset(H,-1,sizeof H);
for(int i=1;i<=N;++i) date[i]=read(H[i]);
sort(date+1,date+N+1);
int tmp=unique(date+1,date+N+1)-date-1;
for(int i=1;i<=N;++i) H[i]=lower_bound(date+1,date+tmp+1,H[i])-date;
for(int i=1;i<=M;++i) E[++num]=(Edge){read<int>(),read<int>(),read<int>()};
Build();
dfs(tot,0);
MakeTree();
Jump();
while(Q--){
int v,x,k;
read(v),read(x),read(k);
int top=Get(v,x);
int l=dfn[top],r=dfn[top]+siz[top]-1;
int ans=Query(root[l],root[r],k,1,N);
if(ans==-1) printf("%d\n",-1);
else printf("%d\n",date[ans]);
}
return 0;
}

LG4197 Peaks的更多相关文章

  1. 【BZOJ-3545&3551】Peaks&加强版 Kruskal重构树 + 主席树 + DFS序 + 倍增

    3545: [ONTAK2010]Peaks Time Limit: 10 Sec  Memory Limit: 128 MBSubmit: 1202  Solved: 321[Submit][Sta ...

  2. *[codility]Peaks

    https://codility.com/demo/take-sample-test/peaks http://blog.csdn.net/caopengcs/article/details/1749 ...

  3. Clustering by density peaks and distance

    这次介绍的是Alex和Alessandro于2014年发表在的Science上的一篇关于聚类的文章[13],该文章的基本思想很简单,但是其聚类效果却兼具了谱聚类(Spectral Clustering ...

  4. Science论文"Clustering by fast search and find of density peaks"学习笔记

    "Clustering by fast search and find of density peaks"是今年6月份在<Science>期刊上发表的的一篇论文,论文中 ...

  5. bzoj 3545&&3551: [ONTAK2010]Peaks &&加强版 平衡树&&并查集合并树&&主席树

    3545: [ONTAK2010]Peaks Time Limit: 10 Sec  Memory Limit: 128 MBSubmit: 635  Solved: 177[Submit][Stat ...

  6. BZOJ 3545: [ONTAK2010]Peaks( BST + 启发式合并 + 并查集 )

    这道题很好想, 离线, 按询问的x排序从小到大, 然后用并查集维护连通性, 用平衡树维护连通块的山的权值, 合并就用启发式合并.时间复杂度的话, 排序是O(mlogm + qlogq), 启发式合并是 ...

  7. bzoj 3551: [ONTAK2010]Peaks加强版

    Description [题目描述]同3545 Input 第一行三个数N,M,Q. 第二行N个数,第i个数为h_i 接下来M行,每行3个数a b c,表示从a到b有一条困难值为c的双向路径. 接下来 ...

  8. BZOJ 3551: [ONTAK2010]Peaks加强版 [Kruskal重构树 dfs序 主席树]

    3551: [ONTAK2010]Peaks加强版 题意:带权图,多组询问与一个点通过边权\(\le lim\)的边连通的点中点权k大值,强制在线 PoPoQQQ大爷题解传送门 说一下感受: 容易发现 ...

  9. BZOJ 3545: [ONTAK2010]Peaks [Splay启发式合并]

    3545: [ONTAK2010]Peaks 题意:带权图,多组询问与一个点通过边权\(\le x\)的边连通的点中点权k大值 又读错题了,输出点一直WA,问的是点权啊 本题加强版强制在线了,那这道题 ...

随机推荐

  1. 一个简单可参考的API网关架构设计

    网关一词较早出现在网络设备里面,比如两个相互独立的局域网段之间通过路由器或者桥接设备进行通信, 这中间的路由或者桥接设备我们称之为网关. 相应的 API 网关将各系统对外暴露的服务聚合起来,所有要调用 ...

  2. English trip -- VC(情景课)3 B Bamily members

    xu言: 今天,好困啊 -__-. . zZ 早点睡吧...适当的休息,才能更好的学习 Vocabulary focus  husband wife uncle aunt brother sister ...

  3. LeetCode--027--移除元素

    问题描述: 给定一个数组 nums 和一个值 val,你需要原地移除所有数值等于 val 的元素,返回移除后数组的新长度. 不要使用额外的数组空间,你必须在原地修改输入数组并在使用 O(1) 额外空间 ...

  4. codeforces 1042d//Petya and Array// Codeforces Round #510 (Div. 2)

    题意:给出一个数组,求其中和小于t的区间数. 先计算前缀和数组sum[i].对当前的sum[i],查询树状数组中有几个比(sum[i]-t)大的数,那么用sum[i]减它就是一个合法区间.再将当前的s ...

  5. 使用dbms_output.put_line打印异常所在的行

    dbms_output.put_line(dbms_utility.format_error_stack); dbms_output.put_line(dbms_utility.format_call ...

  6. AOJ1024 Cleaning Robot 2.0

    先说一说这个OJ:貌似是11区某大学ACM的OJ,叫AIZU ONLINE JUDGE,貌似还可以看到部分犇的代码...跪跪跪 然后知道这个OJ是某场比赛安利的= = 接下来将做法: 首先我们可以发现 ...

  7. js数组与字符串之间的相互转换

    一.数组转字符串 需要将数组元素用某个字符连接成字符串,示例代码如下 <!doctype html> <html> <head> <meta charset= ...

  8. 转mysql半主从同步

    MySQL半同步复制 从MySQL5.5开始,MySQL以插件的形式支持半同步复制.如何理解半同步呢?首先我们来看看异步,全同步的概念   异步复制(Asynchronous replication) ...

  9. C#中使用Spire.docx操作Word文档

    使用docx一段时间之后,一些地方还是不方便,然后就尝试寻找一种更加简便的方法. 之前有尝试过使用Npoi操作word表格,但是太烦人了,随后放弃,然后发现免费版本的spire不错,并且在莫种程度上比 ...

  10. 配置pycharm 一键安装 requirements.txt,一键生成requirements.txt

    如上配置 打开项目,在requirements.txt上点右键,就可以安装了. 安装效果如下: 可以看出运行的命令是   C:\Python\Python36/scripts/pip install ...