zoukankan      html  css  js  c++  java
  • 解题:九省联考2018 IIIDX

    题面

    我当时在考场上划水的时候好像乱搞搞了20pts,然后发现一堆同届的都写了55pts的贪心=。=???

    那就先说那55pts的贪心吧,这个现在看起来还是非常显然的,就是按题意来每一块是分属一个点的,其实这就是棵树,排序之后从叶子往上递增地放就可以了,挺送的=。=

    为什么错了,显然有相同的数的时候可能把一个大点的数放前面也是对的,然后就不优了。如何抢救这个算法哪?

    我们继续刚才那个思路,那么一个数可以填到当前的位置上当且仅当大于等于它的数的数目大于等于这个数所在子树的大小。我们先预留出一个点的子树那些数,然后线段树护维护对于每个位置

    还能填的数的个数。每次在线段树上二分出最小的(有好几个一样的就找最靠右的)大于等于子树预留大小的位置填上去,之后更新小于这个数的位置的能填的数的个数。

    注意每次查询时如果父亲还给这个节点预留着位置先把位置放下来,填完再把这个点的子树留回去

     1 #include<cstdio>
     2 #include<cstring>
     3 #include<algorithm>
     4 using namespace std;
     5 const int N=500005,M=2e6+20;
     6 int val[N],fth[N],siz[N],lst[N];
     7 int n,minn[M],laz[M],rnk[N]; 
     8 double k;
     9 bool cmp(int x,int y)
    10 {
    11     return x>y;
    12 }
    13 void Release(int nde)
    14 {
    15     if(laz[nde])
    16     {
    17         int ls=2*nde,rs=2*nde+1;
    18         minn[ls]+=laz[nde],minn[rs]+=laz[nde];
    19         laz[ls]+=laz[nde],laz[rs]+=laz[nde],laz[nde]=0;
    20     }
    21 }
    22 void Create(int nde,int l,int r)
    23 {
    24     if(l==r)
    25         minn[nde]=l;
    26     else
    27     {
    28         int mid=(l+r)/2,ls=2*nde,rs=2*nde+1;
    29         Create(ls,l,mid),Create(rs,mid+1,r);
    30         minn[nde]=min(minn[ls],minn[rs]);
    31     }
    32 }
    33 void Change(int nde,int l,int r,int ll,int rr,int tsk)
    34 {
    35     if(l>rr||r<ll)
    36         return ;
    37     else if(l>=ll&&r<=rr)
    38         minn[nde]+=tsk,laz[nde]+=tsk;
    39     else
    40     {
    41         int mid=(l+r)/2,ls=2*nde,rs=2*nde+1; Release(nde);
    42         Change(ls,l,mid,ll,rr,tsk),Change(rs,mid+1,r,ll,rr,tsk);
    43         minn[nde]=min(minn[ls],minn[rs]);
    44     }
    45 }
    46 int Query(int nde,int l,int r,int tsk)
    47 {
    48     if(l==r)
    49         return l+(tsk>minn[nde]);
    50     else
    51     {
    52         int mid=(l+r)/2,ls=2*nde,rs=2*nde+1; Release(nde);
    53         return (tsk<=minn[rs])?Query(ls,l,mid,tsk):Query(rs,mid+1,r,tsk);
    54     }
    55 }
    56 int main()
    57 {
    58     scanf("%d%lf",&n,&k);
    59     for(int i=1;i<=n;i++)
    60         scanf("%d",&val[i]),siz[i]=1;
    61     sort(val+1,val+1+n,cmp);
    62     for(int i=n;i;i--)
    63     {
    64         fth[i]=1.0*i/k,siz[fth[i]]+=siz[i];
    65         if(val[i]==val[i+1]) lst[i]=lst[i+1]+1;
    66     }
    67     Create(1,1,n);
    68     for(int i=1;i<=n;i++)
    69     {
    70         if(fth[i]!=fth[i-1]) 
    71             Change(1,1,n,rnk[fth[i]],n,siz[fth[i]]-1);
    72         int ans=Query(1,1,n,siz[i]);
    73         ans+=lst[ans],lst[ans]++,ans-=lst[ans]-1;
    74         rnk[i]=ans,Change(1,1,n,ans,n,-siz[i]);
    75     }
    76     for(int i=1;i<=n;i++)
    77         printf("%d ",val[rnk[i]]);
    78     return 0;
    79 }
    View Code
  • 相关阅读:
    Multi-level CSS3 UL_LI Dropdown Menu
    10个优秀的 HTML5 & CSS3 下拉菜单制作教程
    MVC中@Html.Action的用法(类似自定义控件)
    ASP.NET MVC---自定义HtmlHelper方法
    FormsAuthentication登录ReturnUrl使用绝对路径
    asp.net mvc 身份验证中返回绝对路径的ReturnUrl
    asp.net 2.0 下的表单验证Cookieless属性
    IHttpModule在webconfig中的注册
    中国象棋棋谱浏览器
    刘永富-微信助手
  • 原文地址:https://www.cnblogs.com/ydnhaha/p/10279005.html
Copyright © 2011-2022 走看看