好题好题。


难点在建图,因为图的边数将会决定最小生成树的时间复杂度。我们肯定希望能够只建 \(O(n)\) 级别的边,这样时间复杂度就可以做到 \(O(n\log n)\)。

观察到当 \(i,j,k\) 三个区间能够互相连边时(这里假设 \(a_i<a_j<a_k\)),我们绝对不会连 \((i,k)\) 这条边。

那么假如我们将所有区间按 \(a\) 值大小从小到大排序,每次将当前区间与该区间中所有颜色连边,然后再将这个区间染上新颜色,我们就能保证不会连上述所谓的 \((i,k)\) 边。这很明显是可以珂学解决的。

考虑证明珂朵莉树时间复杂度正确性(实际上也是在证明边数正确性)。

假设原先有 \(x\) 个颜色段,若连 \(y\) 条边,则至少减少 \(y-3\) 个颜色段(除最左边的颜色和最右边的颜色外,中间所有颜色块都一定会被删去,同时全部更新为一个新的颜色段),假如 \(y\) 很小,那么本次操作的单次时间复杂度可忽略不计;假如 \(y\) 很大,则本次操作减少的颜色段数将与花费的时间复杂度在一个量级,就相当于这些参与连边操作的颜色段将不会再次花费时间复杂度,总体时间复杂度依旧正确。

所以我们 极端口胡的 证明了边数级别就是 \(O(n)\),那么珂朵莉树时间复杂度就是 \(O(n\log n)\)。

最小生成树就不用说了。

最终时间复杂度 \(O(n\log n)\),可以通过。

#include<bits/stdc++.h>
#define int long long
using namespace std;
const int N=5e6+5;
int t,n,m,k,ans,fa[N];
struct edge{int x,y,w;}ed[N];
struct line{int l,r,a;}ln[N];
int cmp(edge x,edge y){
return x.w<y.w;
}int cmp2(line x,line y){
return x.a<y.a;
}struct odt{
int l,r;
mutable int v;
bool operator<(const odt &c)const{
return l<c.l;
}
};set<odt>st;
#define iter set<odt>::iterator
struct chtholly{
iter spilt(int x){
iter it=st.lower_bound({x,0,0});
if(it!=st.end()&&(*it).l==x) return it;
it--;if((*it).r<x) return st.end();
int l=(*it).l,r=(*it).r,v=(*it).v;
st.erase(it);st.insert({l,x-1,v});
return st.insert({x,r,v}).first;
}void assign(int l,int r,int v){
iter tr=spilt(r+1),tl=spilt(l);
st.erase(tl,tr);st.insert({l,r,v});
}void con(int l,int r,int id){
iter tr=spilt(r+1),tl=spilt(l);
for(iter it=tl;it!=tr;it++) if((*it).v)
ed[++m]={id,(*it).v,ln[id].a-ln[(*it).v].a};
}
}seniorious;
void init(){
for(int i=1;i<=n;i++) fa[i]=i;
}int find(int x){
return fa[x]=(fa[x]==x?x:find(fa[x]));
}void solve(){
cin>>n,init(),m=ans=0,k=n;
for(int i=1;i<=n;i++)
cin>>ln[i].l>>ln[i].r>>ln[i].a;
sort(ln+1,ln+n+1,cmp2);
st.clear(),st.insert({1,(int)1e9,0});
for(int i=1;i<=n;i++){
seniorious.con(ln[i].l,ln[i].r,i);
seniorious.assign(ln[i].l,ln[i].r,i);
}sort(ed+1,ed+m+1,cmp);
for(int i=1;i<=m;i++){
int x=find(ed[i].x);
int y=find(ed[i].y);
if(x==y) continue;
k--,fa[x]=y,ans+=ed[i].w;
if(k==1){
cout<<ans<<"\n";
return;
}
}cout<<"-1\n";
}signed main(){
ios::sync_with_stdio(0);
cin.tie(0),cout.tie(0);
cin>>t;
while(t--) solve();
return 0;
}/*
In this world where the sun dips in the west.
Set in the heavenly forest.
When this war is over.
The people who do not return and the multitudes who look on.
In the name of justice.
A past that will never die,The fading future.
I'm back.Even if the sun is fading.
Even if I can't see the future.
The light of this moment.
I hope you won't forget.
---- The Happiest Girl in the World
*/

[CF1981E] Turtle and Intersected Segments 题解的更多相关文章

  1. POJ3304:Segments——题解

    http://poj.org/problem?id=3304 题目大意:给n条线段,求是否存在一条直线,将所有线段投影到上面,使得所有投影至少交于一点. ——————————————————————— ...

  2. [CF846C]Four Segments题解

    我们暴力枚举一下\(delim_{1}\) 然后对于每个\(delim_{1}\),O(n)扫一遍+前缀和求出最大\(delim_{0}\)和\(delim_{2}\),然后记录一下它们的位置就行啦 ...

  3. Codeforces Round #535(div 3) 简要题解

    Problem A. Two distinct points [题解] 显然 , 当l1不等于r2时 , (l1 , r2)是一组解 否则 , (l1 , l2)是一组合法的解 时间复杂度 : O(1 ...

  4. Codeforces Round #690 (Div. 3)

    第一次 ak cf 的正式比赛,不正式的是寒假里 div4 的 Testing Round,好啦好啦不要问我为什么没有 ak div4 了,差一题差一题 =.= 不知不觉已经咕了一个月了2333. 比 ...

  5. 题解-CF1389F Bicolored Segments

    题面 CF1389F Bicolored Segments 给 \(n\) 条线段 \([l_i,r_i]\),每条有个颜色 \(t_i\in\{0,1\}\),求最多选出多少条线段,使没有不同颜色的 ...

  6. CodeForces 430A Points and Segments (easy)(构造)题解

    题意:之前愣是没看懂题意...就是给你n个点的坐标xi,然后还规定了Li,Ri,要求给每个点染色,每一组L,R内的点红色和黑色的个数不能相差大于1个,问你能不能染成功,不能输出-1,能就按照输入的顺序 ...

  7. LeetCode题解之Number of Segments in a String

    1.题目描述 2.题目分析 找到字符串中的空格即可 3.代码 int countSegments(string s) { ){ ; } vector<string> v; ; i < ...

  8. PAT甲题题解-1104. Sum of Number Segments (20)-(水题)

    #include <iostream> #include <cstdio> #include <algorithm> #include <string.h&g ...

  9. 【题解】CF1426D Non-zero Segments

    题目戳我 \(\text{Solution:}\) 若\([l,r]\)子段和是\(0,\)则\(sum[r]=sum[l-1].\) 于是我们可以考虑维护当前哪一个前缀和出现过.对于区间\([l,r ...

  10. Codeforces Round #337 (Div. 2) D. Vika and Segments 线段树 矩阵面积并

    D. Vika and Segments     Vika has an infinite sheet of squared paper. Initially all squares are whit ...

随机推荐

  1. JavaScript 绑定this

    1.临时改变函数调用时this的指向 方法:call()与apply(),第一个参数为此次调用时的this指向,如果不传,则则等同于指定全局对象,后面的参数为函数原本的参数 区别:apply()方法传 ...

  2. uniapp多次触发跳转问题

    问题描述:快速点击跳转页面后会闪退到登陆页面 解决方案:重新封装uniapp跳转api,加防抖锁,To.ts import { NavigateToOptions, RedirectToOptions ...

  3. 【报错解决】使用代理后从Github中clone仓库报错

    当电脑使用代理后,会造成Github的clone和push等功能无法正常使用 报错内容:Failed to connect to github.com port 443 after ***** ms: ...

  4. 【PHP】读取本地文件夹中所有图片并显示

    <? //获取文件夹下的所有文件 $dir_str = ''; $imgType = array('gif','png','jpg','jpeg','bmp'); $handle = opend ...

  5. 4.4 服务器上的 Git - 配置服务器

    配置服务器 我们来看看如何配置服务器端的 SSH 访问. 本例中,我们将使用 authorized_keys 方法来对用户进行认证. 同时我们假设你使用的操作系统是标准的 Linux 发行版,比如 U ...

  6. 在不同操作系统上安装 PostgreSQL

    title: 在不同操作系统上安装 PostgreSQL date: 2024/12/26 updated: 2024/12/26 author: cmdragon excerpt: PostgreS ...

  7. Qt/C++音视频开发75-获取本地有哪些摄像头名称/Qt内置函数方式

    一.前言 在需要打开本地摄像头的场景中,有个需求绕不开,那就是如何获取本地有哪些摄像头设备名称,这样可以提供下拉框给用户选择,不然你让用户去填设备名,你觉得用户会知道是啥,他会操作吗?就算你提供了详细 ...

  8. Qt编译数据库插件通用步骤说明

    近期特意花了点时间,在之前数据库集成应用这个组件的基础上再次迭代完善,历经九九八十一难,将Qt的各种数据库插件,十几个Qt版本,全部编译一遍,同时打通了插件形式直连数据库和ODBC数据源连接方式,做过 ...

  9. Qt开源作品6-通用视频控件

    一.前言 在之前做的视频监控系统中,根据不同的用户需要,做了好多种视频监控内核,有ffmpeg内核的,有vlc内核的,有mpv内核的,还有海康sdk内核的,为了做成通用的功能,不同内核很方便的切换,比 ...

  10. 《Bootstrap4Web设计与开发实战》源代码下载

    <Bootstrap4Web设计与开发实战>源代码下载: 链接:https://pan.baidu.com/s/1GaIo390c-l-gsT6-6RaaJA 提取码:fgiq 版权声明: ...