/** [线段树] hdu 3255 Farming#求体积并 扫描水平面,每次用求面积并的方法求每一个水平面的面积并,累加统计 */ #include <stdio.h> #include <string.h> #include <algorithm> using namespace std; #define N 66666 #define L(id) (id << 1) #define R(id) (id << 1 | 1) int n,m,pri[N]; int dy[N],cnt; struct _st { int l,r,sum,cnt; int mid() { return (l + r) >> 1; } }st[N<<2]; struct _cube { int x1,y1,x2,y2,h; void input() { scanf("%d%d%d%d%d",&x1,&y1,&x2,&y2,&h); dy[cnt++] = y1; dy[cnt++] = y2; h = pri[h]; } }cube[N]; struct _seg { int x,y1,y2,flag; _seg(int a = 0,int b = 0,int c = 0,int d = 0) { x = a; y1 = b; y2 = c; flag = d; } }sg[N]; bool cmp(_seg a,_seg b) { return a.x < b.x; } void build(int id,int l,int r) { st[id].l = l; st[id].r = r; st[id].cnt = st[id].sum = 0; if(l == r - 1) return; int mid = st[id].mid(); build(L(id),l,mid); build(R(id),mid,r); } void pushUp(int id) { if(st[id].cnt > 0) { st[id].sum = dy[st[id].r] - dy[st[id].l]; return ; } if(st[id].l + 1== st[id].r) { st[id].sum = 0; return ; } st[id].sum = st[L(id)].sum + st[R(id)].sum; } void update(int id,int l,int r,int fg) { if(st[id].l >= l && st[id].r <= r) { st[id].cnt += fg; pushUp(id); return ; } int mid = st[id].mid(); if(mid >= r) update(L(id),l,r,fg); else if(mid <= l) update(R(id),l,r,fg); else { update(L(id),l,mid,fg); update(R(id),mid,r,fg); } pushUp(id); } int main() { int t,i,j,cas = 0; scanf("%d",&t); while(t--) { cnt = 0; scanf("%d%d",&n,&m); for(i = 1; i <= m; ++i) scanf("%d",pri + i); for(i = 0; i < n; ++i) cube[i].input(); sort(pri,pri + m + 1); sort(dy,dy + cnt); cnt = unique(dy,dy + cnt) - dy; __int64 res = 0LL; for(i = 1; i <= m; ++i) { int tot = 0,l,r; __int64 area = 0LL; for(j = 0; j < n; ++j) if(cube[j].h >= pri[i]) { sg[tot++] = _seg(cube[j].x1,cube[j].y1,cube[j].y2,1); sg[tot++] = _seg(cube[j].x2,cube[j].y1,cube[j].y2,-1); } sort(sg,sg + tot,cmp); build(1,0,cnt); for(j = 0; j < tot - 1; ++j) { l = lower_bound(dy,dy + cnt, sg[j].y1) - dy; r = lower_bound(dy,dy + cnt, sg[j].y2) - dy; update(1,l,r,sg[j].flag); area += 1LL * st[1].sum * (1LL * sg[j+1].x - 1LL * sg[j].x); } res += area * (1LL * pri[i] - 1LL * pri[i-1]); } printf("Case %d: %I64d\n",++cas,res); } return 0; }