传送门:http://www.lydsy.com/JudgeOnline/problem.php?id=2811

【题解】

首先我们先把没看到忍者的段去掉,可以用线段树做。

如果剩下的就是K,那么特判即可。

我们可以把包含关系去掉然后对于剩下的区间,x单增,y单增。

否则的话,我们有一个结论(挺显然的):只有每个区间的右段点才能成为答案。

我们贪心地填肯定是填右端点。

所以我们判断如果右端点填到了前一个位置是否可行即可,如果不可行那么必须填右端点。

二分出这个位置所覆盖的区间(我们钦定填了这里)

然后我们维护fp[i]表示左边i个区间最少填多少,fs[i]表示右边i个区间最少填多少(前缀、后缀)

然后我们判断fp[l]+fs[r]+1是否大于K即可,如果大于,说明一定要填。

# include <stdio.h>
# include <string.h>
# include <algorithm>
// # include <bits/stdc++.h> using namespace std; typedef long long ll;
typedef long double ld;
typedef unsigned long long ull;
const int M = 5e5 + ;
const int mod = 1e9+; # define RG register
# define ST static int n, K, m; int x[M];
struct guard {
int l, r;
guard() {}
guard(int l, int r) : l(l), r(r) {}
friend bool operator < (guard a, guard b) {
return a.l < b.l || (a.l == b.l && a.r > b.r);
}
}a[M], o[M]; int on; bool del[M];
int new_id[M], idx, old_id[M];
int pre[M], nxt[M];
int fp[M], fs[M]; namespace SMT {
int w[M];
# define ls (x<<)
# define rs (x<<|)
inline void edt(int x, int l, int r, int L, int R) {
if(w[x]) return;
if(L <= l && r <= R) {
w[x] = ;
return ;
}
int mid = l+r>>;
if(L <= mid) edt(ls, l, mid, L, R);
if(R > mid) edt(rs, mid+, r, L, R);
}
inline int query(int x, int l, int r, int pos) {
if(w[x]) return ;
if(l == r) return ;
int mid = l+r>>;
if(pos <= mid) return query(ls, l, mid, pos);
else return query(rs, mid+, r, pos);
}
# undef ls
# undef rs
} int main() {
scanf("%d%d%d", &n, &K, &m);
for (int i=; i<=m; ++i) scanf("%d%d%d", &a[i].l, &a[i].r, x+i);
for (int i=; i<=m; ++i) if(x[i] == ) SMT::edt(, , n, a[i].l, a[i].r);
for (int i=; i<=n; ++i) {
if(SMT::query(, , n, i) == ) {
new_id[i] = ++idx, old_id[idx] = i;
// printf("i = %d, idx = %d\n", i, idx);
}
else del[i] = ;
}
if(idx == K) {
for (int i=; i<=n; ++i)
if(!del[i]) printf("%d\n", i);
return ;
}
for (int i=; i<=n; ++i) {
if(!del[i]) pre[i] = i;
else pre[i] = pre[i-];
}
for (int i=n; i; --i) {
if(!del[i]) nxt[i] = i;
else nxt[i] = nxt[i+];
}
for (int i=; i<=m; ++i) {
int nl = nxt[a[i].l], nr = pre[a[i].r];
if(nl <= nr) o[++on] = guard(new_id[nl], new_id[nr]);
}
sort(o+, o+on+);
m = ;
for (int i=; i<=on; ++i) {
while(m && o[i].l >= a[m].l && o[i].r <= a[m].r) --m;
a[++m] = o[i];
}
// for (int i=1; i<=m; ++i)
// printf("%d %d\n", a[i].l, a[i].r);
int cur = ;
for (int i=; i<=m; ++i)
if(a[i].l > cur) fp[i] = fp[i-] + , cur = a[i].r;
else fp[i] = fp[i-];
cur = 1e9;
for (int i=m; i; --i)
if(a[i].r < cur) fs[i] = fs[i+] + , cur = a[i].l;
else fs[i] = fs[i+]; bool have_ans = ; for (int i=, x, l, r, ans1, ans2; i<=m; ++i) {
if(fp[i] != fp[i-]+) continue;
if(a[i].l == a[i].r) {
have_ans = ;
// printf("=%d\n", a[i].r);
printf("%d\n", old_id[a[i].r]);
continue;
}
// 考察每个区间的右端点是否可行
x = a[i].r-;
l = , r = i-, ans1 = ;
while() {
if(r-l<=) {
for (int j=r; j>=l; --j)
if(a[j].r < x) {
ans1 = j;
break;
}
break;
}
int mid = l+r>>;
if(a[mid].r < x) l = mid;
else r = mid;
}
l = i+, r = m, ans2 = m+;
while() {
if(r-l<=) {
for (int j=l; j<=r; ++j)
if(a[j].l > x) {
ans2 = j;
break;
}
break;
}
int mid = l+r>>;
if(a[mid].l > x) r = mid;
else l = mid;
}
// printf("%d %d\n", ans1, ans2);
if(fp[ans1] + fs[ans2] + > K) {
// printf("=%d\n", a[i].r);
printf("%d\n", old_id[a[i].r]);
have_ans = ;
}
} if(!have_ans) puts("-1"); return ;
}

bzoj2811 [Apio2012]Guard的更多相关文章

  1. bzoj2811[Apio2012]Guard 贪心

    2811: [Apio2012]Guard Time Limit: 10 Sec  Memory Limit: 128 MBSubmit: 905  Solved: 387[Submit][Statu ...

  2. bzoj 2811: [Apio2012]Guard【线段树+贪心】

    关于没有忍者的区间用线段树判就好啦 然后把剩下的区间改一改:l/r数组表示最左/最右没被删的点,然后删掉修改后的左边大于右边的:l升r降排个序,把包含完整区间的区间删掉: 然后设f/g数组表示i前/后 ...

  3. bzoj AC倒序

    Search GO 说明:输入题号直接进入相应题目,如需搜索含数字的题目,请在关键词前加单引号 Problem ID Title Source AC Submit Y 1000 A+B Problem ...

  4. Bzoj 3126[Usaco2013 Open]Photo 题解

    3126: [Usaco2013 Open]Photo Time Limit: 10 Sec  Memory Limit: 128 MBSubmit: 335  Solved: 169[Submit] ...

  5. swift中 if let 与 guard let 对比,guard会降低一个分支

    //用if let与guard let实现同一效果,会发现guard降低一个分支 //可以用if var guard var 表示定义的变量能修改值 func test(){ let name:Str ...

  6. CentOS 安装 Zend Guard Loader

    说明:PHP5.3以上的版本不再支持Zend Optimizer,已经被全新的 Zend Guard Loader 取代,下面是安装Zend Guard具体步骤,以下操作均在终端命令行执行 在 Zen ...

  7. Oracle Data Guard的配置

    概述 Oracle Data Guard 是针对企业数据库的最有效和最全面的数据可用性.数据保护和灾难恢复解决方案.它提供管理.监视和自动化软件基础架构来创建和维护一个或多个同步备用数据库,从而保护数 ...

  8. PHP加速处理插件 Zend Optimizer,Zend Guard Loader 和 Zend Opcache 区别

    PHP 5.3.X   以前版本 为  Zend Optimizer PHP 5.3.X   之后 更名为  Zend Guard Loader 可以帮助php执行加密后的php代码 安装实例以Ubu ...

  9. 场景7 Data Guard

    场景7  Data Guard 官方文档 :Oracle Data Guard Concepts and Administration 用于数据容灾,通过主备库同步(主库将redo日志传送到备库,一个 ...

随机推荐

  1. 解决上传app store卡在正在通过iTunes Store鉴定

    打开终端输入代码即可 cd ~ mv .itmstransporter/ .old_itmstransporter/ "/Applications/Xcode.app/Contents/Ap ...

  2. 操作Excel的宏

          有时候在Excel中,需要循环的算每一列的值,而这一列的值是某几列的求和或者某种运算后的结果,比如如下的C4=C3+B4      可以用一个宏来实现,宏代码如下: Dim i As In ...

  3. FJOI 2019 游记

    (FJOI 2019 滚粗记) Day 0 早上刷了一些水题,然后就上路了. (画图3D好好玩) 来得晚只有十几分钟时间看考场,于是连试机题都没有Ak. Day 1 果然我还是太菜了 走过来的时候再讨 ...

  4. 简单工具 & 杂技

    图片压缩: 腾讯智图(http://zhitu.isux.us/) 手机的所有尺寸大小规范: http://screensiz.es/phone 需求: 移动端宽高一致的盒子(因为移动端屏幕宽度不一样 ...

  5. Jmeter学习(三)

    Apache JMeter是Apache组织开发的基于Java的压力测试工具.用于对软件做压力测试,它最初被设计用于Web应用测试,但后来扩展到其他测试.(来自百度) jmeter的特点: 开源免费. ...

  6. Git 相关工具及教程地址

    一.Git GUI 客户端 Git 客户端下载(Windows) TortoiseGit 客户端下载(Windows) Sourcetree 客户端下载(Windows.Mac) Git Extens ...

  7. BZOJ1270[BJWC2008]雷涛的小猫

    雷涛同学非常的有爱心,在他的宿舍里,养着一只因为受伤被救助的小猫(当然,这样的行为是违反学生宿舍管理条例的).在他的照顾下,小猫很快恢复了健康,并且愈发的活泼可爱了. 可是有一天,雷涛下课回到寝室,却 ...

  8. WOW.js 的使用方法

    WOW.js 是一个非常轻量级的动画效果插件,使用它可以组合多种炫酷的效果. 使用WOW.js可以实现我们在网站上常看到的,页面滚动到指定区域时就显示动画的效果. 1.要使用WOW.js必须引入:WO ...

  9. CSP201512-1: 数位之和

    引言:CSP(http://www.cspro.org/lead/application/ccf/login.jsp)是由中国计算机学会(CCF)发起的"计算机职业资格认证"考试, ...

  10. 网络流——poj1273(入门)

    题目链接:排水沟 题意:现有n个排水沟和m个点(其中1是源点,m是汇点),给定n个排水沟所连接的点,求从源点到汇点的最大流量. [EK解法] #include <algorithm> #i ...