原来这么做叫尺取,,,涨姿势了
就是维护两个指针,r 一直扩大直到符合要求
然后将 l 指针向着不断缩小这个区间的方向,直到不符合要求
那么最后删掉的位置到 r 就是一个符合要求的极小区间
不断重复上述过程就能找出最小的
这题就是这么做,线段树维护 max,检查是否符合要求
代码:
#include<algorithm>
#include<iostream>
#include<cstdlib>
#include<cstring>
#include<cstdio>
#include<cctype>
#define lson (x << 1)
#define rson ((x << 1) | 1)
using namespace std;
const int MAXN = 500005, MAXM = 200005;
struct INTERVAL{
int l, r, ul, ur;
bool operator < (const INTERVAL& b) const {
return (r - l) < (b.r - b.l);
}
}itv[MAXN];
struct Node{
int maxn, lzy;
}t[MAXN << 3];
int n, m, sizu, ans = 2147483647;
int uni[MAXN << 1];
inline int rd() {
register int x = 0;
register char c = getchar();
while(!isdigit(c)) c = getchar();
while(isdigit(c)) {
x = x * 10 + (c ^ 48);
c = getchar();
}
return x;
}
inline void pushup(int x) {
t[x].maxn = max(t[lson].maxn, t[rson].maxn);
return;
}
inline void pushdown(int x) {
register int lzy = t[x].lzy;
t[x].lzy = 0;
t[lson].lzy += lzy;
t[lson].maxn += lzy;
t[rson].lzy += lzy;
t[rson].maxn += lzy;
return;
}
void update(int L, int R, int l, int r, int x, int val) {
if(L <= l && r <= R) {
t[x].lzy += val;
t[x].maxn += val;
return;
}
if(t[x].lzy) pushdown(x);
int mid = ((l + r) >> 1);
if(L <= mid) update(L, R, l, mid, lson, val);
if(mid < R) update(L, R, mid + 1, r, rson, val);
pushup(x);
return;
}
int main() {
n = rd(); m = rd();
for(int i = 1; i <= n; ++i) {
itv[i].l = rd(); itv[i].r = rd();
uni[++sizu] = itv[i].l;
uni[++sizu] = itv[i].r;
}
sort(uni + 1, uni + sizu + 1);
sizu = unique(uni + 1, uni + sizu + 1) - uni - 1;
sort(itv + 1, itv + n + 1);
for(int i = 1; i <= n; ++i) {
itv[i].ul = lower_bound(uni + 1, uni + sizu + 1, itv[i].l) - uni;
itv[i].ur = lower_bound(uni + 1, uni + sizu + 1, itv[i].r) - uni;
}
int l = 0, r = 0;
bool GG = false;
while(r < n) {
while(r < n && t[1].maxn < m) {
++r;
update(itv[r].ul, itv[r].ur, 1, sizu, 1, 1);
}
GG = (t[1].maxn < m);
while(l <= r && t[1].maxn >= m) {
++l;
update(itv[l].ul, itv[l].ur, 1, sizu, 1, -1);
}
if(!GG) ans = min(ans, (itv[r].r - itv[r].l) - (itv[l].r - itv[l].l));
}
printf("%d\n", (ans == 2147483647 ? -1 : ans));
return 0;
}
原文:https://www.cnblogs.com/xcysblog/p/9780432.html