扫描线是一种算法思想,其特征为将静态 \(k\) 维问题转化为动态 \(k - 1\) 维问题。动态 \(k - 1\) 维问题往往需要数据结构维护。
例题
【模板】扫描线
题意:求矩形面积并,其中每个举行的四边平行于坐标轴。
考虑扫描线,将静态 \(2\) 维问题转化为动态 \(1\) 维问题。
具体的,考虑按 \(y\) 轴排序每根与 \(x\) 轴平行的线段。随后逐个枚举并使用线段树维护。这里不特别讲线段树维护,可以理解为需要一个区间加查区间非零个数(保证全局查询)的线段树,可以自行去看题解。
代码:
#include <iostream>
#include <algorithm>
#define int long long
#define rep(i, l, r) for (int i = l; i <= r; i++)
#define per(i, l, r) for (int i = l; i >= r; i--)
using namespace std;
struct segment {
int y, x1, x2, mk;
segment(int y = 0, int x1 = 0, int x2 = 0, int mk = 0): y(y), x1(x1), x2(x2)\
, mk(mk) {}
bool operator<(segment o) {
return y < o.y;
}
}sg[2000010];
int x[2000010], x1, y1, x2, y2, n, cnt, ans;
struct d {
int l, r, tot, len;
d(int l = 0, int r = 0, int tot = 0, int len = 0):l(l), r(r), tot(tot)\
, len(len) {}
}dat[8000010];
void pushUp(int p) {
if (dat[p].tot > 0) {
dat[p].len = x[dat[p].r + 1] - x[dat[p].l];
} else {
dat[p].len = dat[2 * p].len + dat[2 * p + 1].len;
}
}
void build(int p, int l, int r) {
if (l == r) {
dat[p] = d(l, r, 0, 0);
} else {
dat[p] = d(l, r, 0, 0);
int mid = (l + r) / 2;
build(2 * p, l, mid);
build(2 * p + 1, mid + 1, r);
}
}
void modify(int p, int cl, int cr, int v) {
int l = dat[p].l, r = dat[p].r;
// cout << p << " " << l << " " << r << "\n";
if (x[r + 1] <= cl || x[l] >= cr) {
return;
}
if (x[l] >= cl && x[r + 1] <= cr) {
dat[p].tot += v;
pushUp(p);
return;
}
modify(2 * p, cl, cr, v);
modify(2 * p + 1, cl, cr, v);
pushUp(p);
}
signed main() {
cin >> n;
rep (i, 1, n) {
cin >> x1 >> y1 >> x2 >> y2;
sg[2 * i - 1] = segment(y1, x1, x2, 1);
sg[2 * i] = segment(y2, x1, x2, -1);
x[2 * i - 1] = x1;
x[2 * i] = x2;
}
n *= 2;
sort(sg + 1, sg + n + 1);
sort(x + 1, x + n + 1);
cnt = unique(x + 1, x + n + 1) - x - 1;
build(1, 1, cnt - 1);
rep (i, 1, n - 1) {
modify(1, sg[i].x1, sg[i].x2, sg[i].mk);
rep (j, 1, 3) {
// cout << dat[j].l << " " << dat[j].r << " " << dat[j].tot << " " << dat[j].len << "\n";
}
// cout << dat[1].len << "\n";
ans += dat[1].len * (sg[i + 1].y - sg[i].y);
}
cout << ans << "\n";
}
标签:dat,int,笔记,学习,扫描线,x2,x1,sg
From: https://www.cnblogs.com/IANYEYZ/p/18331170