POJ 1151 && HDU 1542 Atlantis
做模板
#include<cstdio>
#include<cstring>
#include<algorithm>
#include<vector>
#include<queue>
#include<cmath>
using namespace std;
typedef long long LL;
const int MAXN = 2000 + 5;
int Col[MAXN<<4],q,cnt,res,n,m,k;
double X[MAXN<<4],Sum[MAXN<<4];
struct node {
double l,r,h;
int d;
node() {}
node(double l,double r,double h,int d):l(l),r(r),h(h),d(d) {}
bool operator < (const node & tmp) const {
return h < tmp.h;
}
}tree[MAXN];
void pushup(int rt,int l,int r) {
if (Col[rt]) Sum[rt] = X[r+1]-X[l];
else if (l==r) Sum[rt] = 0;
else Sum[rt]=Sum[rt<<1]+Sum[rt<<1|1];
}
void update(int L, int R, int val,int x,int l, int r) {
if(L<=l && r<= R) {
Col[x]+=val;
pushup(x,l,r);
return ;
}
int mid=(l+r)/2;
if(L<=mid) update(L,R,val,x<<1,l,mid);
if(R>mid) update(L,R,val,x<<1|1,mid+1,r);
pushup(x,l,r);
}
int main() {
int cas = 1;
// freopen("1.in","r",stdin);
while(~scanf("%d",&q)&&q) {
n=0,m=0;
for(int i=1;i<=q;i++) {
double x1,y1,x2,y2;
scanf("%lf%lf%lf%lf",&x1,&y1,&x2,&y2);
tree[++m]=node(x1,x2,y1,1);
X[++n]=x1;
tree[++m]=node(x1,x2,y2,-1);
X[++n]=x2;
}
sort(X+1,X+n+1);
sort(tree+1,tree+m+1);
k=1;
for(int i=2;i<=n;i++) {
if(X[i]!=X[i-1]) X[++k]=X[i];
}
memset(Sum,0,sizeof(Sum));
memset(Col,0,sizeof(Col));
double ans=0;
for(int i=1;i<m;i++){
int l=lower_bound(X,X+k,tree[i].l)-X;
int r=lower_bound(X,X+k,tree[i].r)-X-1;//利用[ , ),这个区间性质,左闭右开
update(l,r,tree[i].d,1,1,k-1);
ans+=Sum[1]*(tree[i+1].h-tree[i].h);
}
printf("Test case #%d\nTotal explored area: %.2f\n\n",cas++ , ans);
}
return 0;
}
POJ的编译器果然很精妙。
事实上,对于printf(),无论是%f还是%lf,效果都是一样的。
因为,遇到float,printf()会将float类型自动提升到double,所以不会有什么问题。
而且严格地讲,printf()并没有对于%lf的定义,虽然很多编译器会接受,所以最好使用%f。
然而POJ的并不接受。QAQ
2017 ACM/ICPC 南宁区 网络赛 Overlapping Rectangles
Overlapping Rectangles
也是一道一样题目,稍微改改板子就行~
#include<cstdio>
#include<cstring>
#include<algorithm>
#include<vector>
#include<queue>
#include<cmath>
using namespace std;
typedef long long LL;
const int MAXN = 2000 + 5;
int Col[MAXN<<4],q,cnt,res,n,m,k;
double X[MAXN<<4],Sum[MAXN<<4];
struct node {
double l,r,h;
int d;
node() {}
node(double l,double r,double h,int d):l(l),r(r),h(h),d(d) {}
bool operator < (const node & tmp) const {
return h < tmp.h;
}
}tree[MAXN];
void pushup(int rt,int l,int r) {
if (Col[rt]) Sum[rt] = X[r+1]-X[l];
else if (l==r) Sum[rt] = 0;
else Sum[rt]=Sum[rt<<1]+Sum[rt<<1|1];
}
void update(int L, int R, int val,int x,int l, int r) {
if(L<=l && r<= R) {
Col[x]+=val;
pushup(x,l,r);
return ;
}
int mid=(l+r)/2;
if(L<=mid) update(L,R,val,x<<1,l,mid);
if(R>mid) update(L,R,val,x<<1|1,mid+1,r);
pushup(x,l,r);
}
int main() {
int cas = 1;
// freopen("1.in","r",stdin);
while(~scanf("%d",&q)) {
if(q==0){
printf("*\n");
return 0;
}
n=0,m=0;
for(int i=1;i<=q;i++) {
double x1,y1,x2,y2;
scanf("%lf%lf%lf%lf",&x1,&y1,&x2,&y2);
tree[++m]=node(x1,x2,y1,1);
X[++n]=x1;
tree[++m]=node(x1,x2,y2,-1);
X[++n]=x2;
}
sort(X+1,X+n+1);
sort(tree+1,tree+m+1);
k=1;
for(int i=2;i<=n;i++) {
if(X[i]!=X[i-1]) X[++k]=X[i];
}
memset(Sum,0,sizeof(Sum));
memset(Col,0,sizeof(Col));
double ans=0;
for(int i=1;i<m;i++){
int l=lower_bound(X,X+k,tree[i].l)-X;
int r=lower_bound(X,X+k,tree[i].r)-X-1;//利用[ , ),这个区间性质,左闭右开
update(l,r,tree[i].d,1,1,k-1);
ans+=Sum[1]*(tree[i+1].h-tree[i].h);
}
printf("%.0f\n",ans);
}
return 0;
}