【训练题21:思维(线段相交问题)】F. The Treasure of The Segments | CF 690 (Div 3)

F. The Treasure of The Segments

难度比

− 908 13614 -\frac{908}{13614} 13614908

题意

给你 n n n 条线段,每条位置 [ l i , r i ] [l_i,r_i] [li,ri]
让你删掉最少数量的线段后,剩下的线段集合至少有一个线段 s s s,满足该线段与其他线段都相交(交点可以是点也可以是线段)

问你,最少删掉多少条线段?

数据范围

1 ≤ n ≤ 2 × 1 0 5 1\le n\le 2\times 10^5 1n2×105
1 ≤ l i ≤ r i ≤ 1 0 9 1\le l_i\le r_i\le 10^9 1liri109

思路

  • 什么情况两条线段是相交的? s i ∩ s j    ⟺    max ⁡ ( l i , l j ) ≤ min ⁡ ( r i , r j ) s_i\cap s_j\iff \max(l_i,l_j) \le \min(r_i,r_j) sisjmax(li,lj)min(ri,rj)
  • 这样不好考虑。我们考虑反面:什么情况两条线段是不相交的? l i > r j ∨ r i < l j l_i > r_j \vee r_i < l_j li>rjri<lj
  • 这个情况就比较好考虑了。我们对于某一条线段,计算出有多少条线段的右端点小于 l i l_i li,以及多少条线段的左端点大于 r i r_i ri,然后所有答案取 min ⁡ \min min即可
  • 计算数量使用 l o w e r _ b o u n d lower\_bound lower_bound 即可,注意可能比较难写 (?) 注意一些小细节。

核心代码

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

/*
 _            __   __          _          _
| |           \ \ / /         | |        (_)
| |__  _   _   \ V /__ _ _ __ | |     ___ _
| '_ \| | | |   \ // _` | '_ \| |    / _ \ |
| |_) | |_| |   | | (_| | | | | |___|  __/ |
|_.__/ \__, |   \_/\__,_|_| |_\_____/\___|_|
        __/ |
       |___/
*/
const int MAX = 2e5+50;

struct node{
    int lef;
    int rig;
}aa[MAX];

vector<int>V1,V2;

int main()
{
    int T;scanf("%d",&T);
    while(T--){
        V1.clear();V2.clear();
        int n;scanf("%d",&n);
        for(int i = 0;i < n;++i){
            scanf("%d%d",&aa[i].lef,&aa[i].rig);
            V1.push_back(aa[i].lef);
            V2.push_back(aa[i].rig);
        }
        sort(V1.begin(),V1.end());
        sort(V2.begin(),V2.end());
        int ans = INF;
        for(int i = 0;i < n;++i){
            int num1 = lower_bound(V2.begin(),V2.end(),aa[i].lef) - V2.begin();
            int num2 = max(0,n - (int)(upper_bound(V1.begin(),V1.end(),aa[i].rig) - V1.begin()));
            ans = min(ans,num1 + num2);
        }
        printf("%d\n",ans);
    }
    return 0;
}
评论 2
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值