题意
在n*m的平面上有k条射线,问把这个平面切成多少块?
思路
预处理一下,按x左边排序,type=1表示开始的位置,type=2表示结束的位置,用线段树维护y轴,单点更新,区间查询.
代码
#include<bits/stdc++.h>
using namespace std;
const int maxn=1e5+10;
int tree[maxn<<2];
int c;
int n,m,q;
void built(int rt,int l,int r){
tree[rt]=0;
if(l==r) return ;
int mid=(l+r)>>1;
built(rt<<1,l,mid);
built(rt<<1|1,mid+1,r);
}
void update(int pos,int val,int l=1,int r=c,int rt=1){
if(l==r){
tree[rt]+=val;
return;
}
int mid=(l+r)>>1;
if(pos<=mid) update(pos,val,l,mid,rt<<1);
else update(pos,val,mid+1,r,rt<<1|1);
tree[rt]=tree[rt<<1]+tree[rt<<1|1];
}
int query(int ql,int qr,int l=1,int r=c,int rt=1){
if(ql<=l&&qr>=r) return tree[rt];
int mid=(l+r)>>1;
int ans=0;
if(ql<=mid) ans+=query(ql,qr,l,mid,rt<<1);
if(qr>mid) ans+=query(ql,qr,mid+1,r,rt<<1|1);
return ans;
}
struct node{
int x,y1,y2,type;
bool operator <(const node& a) const {
return x==a.x?type<a.type:x<a.x;
}
}a[maxn*2];
int b[maxn];
int getid(int x) {
return lower_bound(b + 1, b + c + 1, x) - b;
}
int main() {
int _;scanf("%d", &_);
while(_--) {
scanf("%d%d%d", &n, &m, &q);
int tot = 0;
b[q+1] = 0, b[q+2] = m;
for(int i=1;i<=q;i++){
int x,y;char s[2];
scanf("%d%d%s",&x,&y,s);
b[i]=y;
if(s[0]=='L'){
a[++tot]={0,y,0,1};
a[++tot]={x+1,y,0,2};
}
else if(s[0]=='R'){
a[++tot]={x,y,0,1};
a[++tot]={n+1,y,0,2};
}
else if(s[0]=='U'){
a[++tot]={x,y,m,3};
}
else a[++tot]={x,0,y,3};
}
sort(a+1,a+tot+1);
sort(b+1,b+q+3);
c=unique(b+1,b+q+3)-b-1;
built(1, 1, c);
int ans = 1;
for(int i = 1; i <= tot; ++i) {
if(a[i].type == 1) update(getid(a[i].y1), 1);
else if(a[i].type == 2) update(getid(a[i].y1), -1);
else ans += query( getid(a[i].y1), getid(a[i].y2));
}
printf("%d\n", ans);
}
//system("pause");
return 0;
}