zoukankan      html  css  js  c++  java
  • 洛谷P2334

    不知道写点啥好了,把昨天晚上做的屑题放上来好了。

    不到 15 mins 口胡了个很傻逼的方程,然后玄学改了改数据范围就过了。

    看到转移,每次只能走一格,只有三个方向可以走,所以考虑枚举走到当前格子的状态。

    由于有个什么周期限制,再考虑枚举走到当前格子的时间。

    (f_{i,j}) 表示在时间 (i) 走到了格子 (j)

    显然有转移方程式:

    [f_{i,j}=min{f_{i-1,j},f_{i-1,j-1},f_{i-1,j+1}}+v_{i mod t_j,j} ]

    其中 (t_j) 表示格子 (j) 的周期,(v_{imod t_j,j}) 表示在这个时间这个格子收到的伤害。特别的,当 (imod t_j=0) 时要变成 (v_{t_j,j})

    这式子第一眼看上去很 naive 对吗?我一开始也这么觉得。

    当然,由于并没有规定要在什么时间内走到终点,所以我们枚举这个时间。

    看到 (nle 1000),然后我猜测最差情况下,每个格子的每种周期攻击都承受时,可以到 (10000) 步。

    当然也没有什么依据,但是比较保险,而且这个范围完全可以过。

    signed main(){
      n=read();
      memset(f,INF,sizeof f);
      for(int i=0;i<=n+10000;i++) f[i][0]=0;
      for(int i=1,x;i<=n;i++){
        d[i]=read();
        for(int j=1;j<=d[i];j++)
          c[i][j]=read();
      }
      
      for(int i=1;i<=n+10000;i++){
        for(int j=1,tim;j<=min(n+1,i);j++){
          if(d[j]) tim=i%d[j];
          else tim=11;
          if(tim==0) tim=d[j];
          f[i][j]=min(f[i][j],f[i-1][j]+c[j][tim]);
          f[i][j]=min(f[i][j],f[i-1][j-1]+c[j][tim]);
          f[i][j]=min(f[i][j],f[i-1][j+1]+c[j][tim]);
        }
      }
      int ans=INF;
      for(int i=n+1;i<=n+10000;i++)
        ans=min(ans,f[i][n+1]);
      cout<<ans<<endl;
      return 0;
    }
    

    写的比较难看,毕竟本来对这个式子没啥信心,不过还可以。

  • 相关阅读:
    利用socket.io实现多人聊天室(基于Nodejs)
    【翻译】Ext JS 5的平板支持
    Spring IoC、DI入门小程序
    初学hibernate之缓存
    获取谷歌浏览器缓存视频方法
    JavaScript模块化学习基础
    HTTP Content-type
    初学Hibernate持久化
    初学Hibernate主键生成策略
    初学Hibernate之Query扩展
  • 原文地址:https://www.cnblogs.com/KnightL/p/14965046.html
Copyright © 2011-2022 走看看