【分块】bzoj2957 楼房重建

http://www.cnblogs.com/wmrv587/p/3843681.html

ORZ 分块大爷。思路很神奇也很清晰。

把 块内最值 和 块内有序 两种良好的性质结合起来,非常棒地解决了这个问题。

图中黑色的楼房即为每个块内的“可视序列”,显而易见,在块内它们的K(斜率)是单增的。

由于上图中第一个块的maxK比后面两个块的maxK都要大,所以后两个块对答案没有贡献,这也是显然的。这就是维护maxK的意义所在。

否则,若一个块可以更新maxK的话,则其中的部分楼房是“可见的”,具体来说,就是在那个比之前的maxK要大的楼房的后面的在可视序列中的楼房数。<---请从方链接看原版题解。

另外,并不会像他说的,基本不会T,如果把块大小开得合适。

 1 #include<cstdio>
 2 #include<algorithm>
 3 #include<vector>
 4 #include<cmath>
 5 #include<cstring>
 6 using namespace std;
 7 inline double max(const double &a,const double &b){return a>b?a:b;}
 8 vector<double>See[320];
 9 double k[100001];
10 int sz,sum,l[320],r[320],num[100001],n,m,x,y;
11 double maxv[320];
12 int Res,Num;char C,CH[12];
13 inline int G()
14 {
15     Res=0;C='*'; 
16     while(C<'0'||C>'9')C=getchar();
17     while(C>='0'&&C<='9'){Res=Res*10+(C-'0');C=getchar();}
18     return Res;
19 }
20 inline void P(int x)
21 {
22     Num=0;if(!x){putchar('0');puts("");return;}
23     while(x>0)CH[++Num]=x%10,x/=10;
24     while(Num)putchar(CH[Num--]+48);
25     puts("");
26 }
27 void makeblock()
28 {
29     memset(maxv,0,sizeof(maxv));
30     sz=sqrt((double)n*1.05);
31     for(sum=1;sum*sz<n;sum++)
32       {
33         l[sum]=(sum-1)*sz+1;
34         r[sum]=sum*sz;
35         for(int i=l[sum];i<=r[sum];i++) num[i]=sum;
36       }
37     l[sum]=sz*(sum-1)+1;
38     r[sum]=n;
39     for(int i=l[sum];i<=r[sum];i++) num[i]=sum;
40 }
41 inline void update()
42 {
43     k[x]=(double)y/x;
44     See[num[x]].clear();
45     maxv[num[x]]=0.0;
46     for(int i=l[num[x]];i<=r[num[x]];i++)
47       if(k[i]>maxv[num[x]])
48         {
49           maxv[num[x]]=k[i];
50           See[num[x]].push_back(k[i]);
51         }
52 }
53 inline void query()
54 {
55     int ans=0;double tmp=0.0;
56     for(int i=1;i<=sum;i++)
57       if(!See[i].empty())
58         {
59             ans+=See[i].end()-upper_bound(See[i].begin(),See[i].end(),tmp);
60             tmp=max(tmp,maxv[i]);
61         }
62     P(ans);
63 }
64 int main()
65 {
66     n=G();m=G();makeblock();
67     for(int i=1;i<=m;i++){x=G();y=G();update();query();}
68     return 0;
69 }

 

posted @ 2014-10-14 16:24  AutSky_JadeK  阅读(400)  评论(0编辑  收藏  举报
TVアニメ「Charlotte(シャーロット)」公式サイト TVアニメ「Charlotte(シャーロット)」公式サイト