zoukankan      html  css  js  c++  java
  • [POI2010]Frog

    题目大意:
      一个数轴上有n个点,现在你要在这些点上跳。
      每次跳的时候你只能跳到离这个点第k近的点上,而且要连续跳m次。
      问从每一个点出发,最后分别会在哪一个点结束。

    思路:
      首先可以维护一个大小为k+1的队列,使得离当前点第k远的点一定在这个队列中。
      显然当i=1时,队列的范围是[1,k+1],然后当pos[i]-pos[l]>pos[l+k+1]-pos[i]时,队列往右移一个点。
      至于第k近的点,则要么是左端点,要么是右端点,只要比一下哪个更远即可。
      这样就可以O(n)地求出离每个点第k近的点。
      但是现在我们要跳m次,而m很大,很显然不能暴力跳,而用LCA之类的也不行,因为到最顶上是一个环。
      考虑把每一次跳的过程看作一个置换,那么总共要进行m次置换。
      而这些置换可以通过类似于快速幂的方法实现。
      把所有的点置换一次是O(n)的,总共会有O(log m)次置换,所以时间复杂度是O(n log m)的。

     1 #include<cstdio>
     2 #include<cctype>
     3 typedef long long int64;
     4 inline int64 getint() {
     5     register char ch;
     6     while(!isdigit(ch=getchar()));
     7     register int64 x=ch^'0';
     8     while(isdigit(ch=getchar())) x=(((x<<2)+x)<<1)+(ch^'0');
     9     return x;
    10 }
    11 const int N=1000001;
    12 int64 pos[N];
    13 int next[N],tmp[N],ans[N];
    14 int main() {
    15     const int n=getint(),k=getint();
    16     register int64 m=getint();
    17     for(register int i=1;i<=n;i++) pos[i]=getint();
    18     for(register int i=1,l=1;i<=n;i++) {
    19         while(l+k<n&&pos[i]-pos[l]>pos[l+k+1]-pos[i]) l++;
    20         next[i]=(pos[i]-pos[l]>=pos[l+k]-pos[i])?l:l+k;
    21     }
    22     for(register int i=1;i<=n;i++) ans[i]=i;
    23     for(;m;m>>=1) {
    24         if(m&1) {
    25             for(register int i=1;i<=n;i++) {
    26                 ans[i]=next[ans[i]];
    27             }
    28         }
    29         for(register int i=1;i<=n;i++) tmp[i]=next[next[i]];
    30         for(register int i=1;i<=n;i++) next[i]=tmp[i];
    31     }
    32     for(register int i=1;i<=n;i++) {
    33         printf("%d%c",ans[i]," 
    "[i==n]);
    34     }
    35     return 0;
    36 }
  • 相关阅读:
    正则匹配
    去除数组、对象某个元素
    换行
    a标签问题
    vue的坑
    宽度100%-20px ,css样式设置超出部分...
    搜狗密码框自带小键盘问题
    阻止button刷新页面
    Java IO流经典练习题
    Java中统计字符串中各个字符出现的次数
  • 原文地址:https://www.cnblogs.com/skylee03/p/8044768.html
Copyright © 2011-2022 走看看