半年前就听说过一种名为扫描线的神秘科技,但实际上学过后会发现其实就是一种线段树的用法,其中扫描线的线段树还和普通的线段树有所不同,一个是每个节点实际上是映射1e9的值,其次需要同时维护两棵线段树:flag记录当先节点是否全部被覆盖(只记录最深处的值且不pushup);sum记录当先线段中扫描到的长度(需要pushup但由于每次都是只用访问sum[1]所以不用pushdown)。另外需要注意的另外一点就是线段树是只根据左节点的建立的,所以有一些操作和一般的线段树不同。
总之,扫描线原理不难但是需要考虑的细节很多,代码中已经标记,不能写错了!
#include <bits/stdc++.h>
#define x first
#define y second
#define mid (l + r >> 1)
#define lo (o << 1)
#define ro (lo | 1)
using namespace std;
typedef long long ll;
typedef long double ld;
typedef pair<int, int> pii;
typedef vector<int> vi;
const int maxn = 2e5 + 10;
const int inf = 0x3f3f3f3f;
const ll linf = 0x3f3f3f3f3f3f3f3f;
const ll mod = 998244353;
struct tri{int x,y,z;};
struct A
{
int l,r,h,flag;
}brr[maxn];//arr代表横坐标,brr代表横着的线段信息
int n,tot,arr[maxn],flag[maxn<<2];
ll