zoukankan      html  css  js  c++  java
  • 栅栏

    问题描述
    家有一条栅栏,由n个木板顺序组成,第i个木板的高度是Ai。现在小镇上流行在栅栏
    上画矩形,所以小v也要在自家的栅栏上画。若要在区间 [x,x+k-1] 这个区间画一个宽度为
    k的矩形 (1≤x≤n-k+1) ,为了美观,高度一定是这个区间里高度最低的木板。现在小v心中
    有m个理想的宽度,第i个为Ki,(Ki与Kj之间可能一样)。他想知道对于每个Ki,其矩形高度的
    期望。
    输入格式
    第一行一个整数n,表示木板的数目。
    第二行有n个正整数,第i个数表示第i个木板的高度。
    第三行一个整数m,表示理想宽度的数目。
    第四行有m个正整数,第i个数表示
    心中理想的第i个宽度Ki。
    输出格式
    输出m行实数,第i行表示宽度为Ki的矩形高度的期望。答案保留5位小数。
    样例输入输出
    样例输入1
    3
    3 2 1
    4
    1 2 3 1样例输出1
    2.00000
    1.50000
    1.00000
    2.00000
    限制与约定
    对于100%的数据,

    n<=1e6,m<=1e6,1<=Ai<=1e9,1<=Ki<=n

    题解:

    显然处理出L[i],R[i]表示左右第一个比i小的数,显然这个区间内跨越i的都是属于i的贡献

    我们就处理L[i],R[i]之间端点,枚举i-L[i] 或 i-R[i] 显然处理较小的那个,然后差分加减即可

    复杂度O(nlogn) 开始还以为和暴力是一样的..........................................................................

      1 #include <algorithm>
      2 #include <iostream>
      3 #include <cstdlib>
      4 #include <cstring>
      5 #include <cstdio>
      6 #include <cmath>
      7 #define ls (node<<1)
      8 #define rs (node<<1|1)
      9 using namespace std;
     10 typedef long long ll;
     11 const int N=1000005,INF=2e9;
     12 int gi(){
     13     int str=0;char ch=getchar();
     14     while(ch>'9' || ch<'0')ch=getchar();
     15     while(ch>='0' && ch<='9')str=(str<<1)+(str<<3)+ch-48,ch=getchar();
     16     return str;
     17 }
     18 int a[N],n,m,ques[N],b[N],c[N],num=0,L[N],R[N];ll ans[N];
     19 namespace Deal1{
     20     int Tree[N<<2];
     21     void build(int l,int r,int node){
     22         if(l==r){
     23             Tree[node]=a[l];
     24             return ;
     25         }
     26         int mid=(l+r)>>1;
     27         build(l,mid,ls);build(mid+1,r,rs);
     28         Tree[node]=Tree[ls]<Tree[rs]?Tree[ls]:Tree[rs];
     29     }
     30     int query(int l,int r,int node,int sa,int se){
     31         if(l>se || r<sa)return INF;
     32         if(sa<=l && r<=se)return Tree[node];
     33         int mid=(l+r)>>1;
     34         int q1=query(l,mid,ls,sa,se),q2=query(mid+1,r,rs,sa,se);
     35         return q1<q2?q1:q2;
     36     }
     37     void main(){
     38         int k,tmp;
     39         build(1,n,1);
     40         for(int i=1;i<=num;i++){
     41             k=c[i];
     42             for(int j=1;j+k-1<=n;j++){
     43                 tmp=query(1,n,1,j,j+k-1);
     44                 ans[k]+=tmp;
     45             }
     46         }
     47         double ret;
     48         for(int i=1;i<=m;i++){
     49             ret=(double)ans[ques[i]]/(n-ques[i]+1);
     50             printf("%.5lf
    ",ret);
     51         }
     52    }
     53 }
     54 namespace Deal2{
     55     int L[N],R[N],q[N];ll ans[N];
     56     void prework(){
     57         int r=1;q[0]=0;
     58         for(int i=1;i<=n;i++){
     59             while(1<=r && a[i]<a[q[r]])r--;
     60             L[i]=q[r]+1;q[++r]=i;
     61         }
     62         r=0;q[0]=n+1;
     63         for(int i=n;i>=1;i--){
     64             while(1<=r && a[i]<=a[q[r]])r--;
     65             R[i]=q[r]-1;q[++r]=i;
     66         }
     67     }
     68     void Getanswer(){
     69         int l,r;
     70         for(int i=1;i<=n;i++){
     71             l=i-L[i]+1;r=R[i]-i+1;
     72             if(l>r)swap(l,r);
     73             for(int j=1;j<=l;j++)
     74                 ans[j]+=a[i],ans[j+r]-=a[i];
     75         }
     76             for(int i=1;i<=c[num];i++)ans[i]+=ans[i-1];
     77     }
     78     void main(){
     79         prework();
     80         Getanswer();
     81         double ret;
     82         for(int i=1;i<=m;i++){
     83             ret=(double)(ans[ques[i]])/(n-ques[i]+1);
     84             printf("%.5lf
    ",ret);
     85         }
     86     }
     87 }
     88 void work(){
     89     n=gi();
     90     for(int i=1;i<=n;i++)a[i]=gi();
     91       m=gi();
     92       for(int i=1;i<=m;i++)ques[i]=b[i]=gi();
     93       sort(b+1,b+m+1);
     94       for(int i=1;i<=m;i++)if(b[i]!=b[i+1])c[++num]=b[i];
     95     if(n<=2000)Deal1::main();
     96     else
     97     Deal2::main();
     98 }
     99 int main()
    100 {
    101     freopen("fence.in","r",stdin);
    102     freopen("fence.out","w",stdout);
    103     work();
    104     return 0;
    105 }
  • 相关阅读:
    对NumPy中dot()函数的理解
    使用Boostrap框架写一个登录注册界面
    两种方法实现asp.net方案的前后端数据交互(aspx文件、html+ashx+ajax)
    将包含经纬度点位信息的Excel表格数据导入到ArcMap中并输出成shapefile
    [ArcGIS API for JavaScript 4.8] Sample Code-Popups-1-popupTemplate的概念和popup中属性字段值的多种表现形式
    [python爬虫]Requests-BeautifulSoup-Re库方案--robots协议与Requests库实战
    [python爬虫]Requests-BeautifulSoup-Re库方案--Requests库介绍
    [ArcGIS API for JavaScript 4.8] Sample Code-Get Started-widgets简介
    [ArcGIS API for JavaScript 4.8] Sample Code-Get Started-popups简介
    [ArcGIS API for JavaScript 4.8] Sample Code-Get Started-layers简介
  • 原文地址:https://www.cnblogs.com/Yuzao/p/7202141.html
Copyright © 2011-2022 走看看