博客
关于我
强烈建议你试试无所不能的chatGPT,快点击我
bzoj2259
阅读量:5954 次
发布时间:2019-06-19

本文共 1408 字,大约阅读时间需要 4 分钟。

这道题很不错,首先读入方式有一种跳跃的既视感:

读入Si之后,我们可以直接往后跳Si,可以想到最短路,设序列为a[],我们设n+1是终点
如果i+a[i]<=n+1 那么i-->i+a[i] 权值为0 否则i-->n+1 权值为i+a[i]-n
注意这可以算是一种非常经典的区间建图的方法
下面我们解决调整某个数,我们比划一下就知道,在相邻两点连一条权值为1的无向边即可
然后我们可以跑最短路了
但是看到n<=1000000是不是感觉dij+heap有点虚?实际上对这个图我们直接宽搜就好了
为什么?仔细研究发现,大部分边权值不是1就是0,只有一些点到终点的权值是不和谐的
但这有什么关系呢?我们到快到终点的那个点直接计算比较取最优即可

1 const inf=1000000007; 2  3 var q,f,d:array[0..1000010] of longint; 4     ans,n,i,h,r:longint; 5  6 function min(a,b:longint):longint; 7   begin 8     if a>b then exit(b) else exit(a); 9   end;10 11 procedure add(x,w:longint);12   begin13     if (x<1) or (x>n+1) then exit;14     while d[x]>inf do15     begin16       d[x]:=w;17       inc(r);18       q[r]:=x;19       if f[x]>n then20       begin21         ans:=min(ans,f[x]-n-1+d[x]);22         exit;23       end;24       x:=f[x];25     end;26   end;27 28 procedure work;29   var x:longint;30   begin31     if f[1]>n then32     begin33       ans:=f[1]-n-1;34       exit;35     end;36     h:=1;37     add(f[1],0);38     while (h<=r) and (d[n+1]>inf) do39     begin40       x:=q[h];41       add(x-1,d[x]+1);42       add(x+1,d[x]+1);43       inc(h);44     end;45   end;46 47 begin48   readln(n);49   for i:=1 to n do50   begin51     read(f[i]);52     f[i]:=f[i]+i+1;53   end;54   ans:=inf;55   fillchar(d,sizeof(d),127);56   work;57   ans:=min(ans,d[n+1]);58   writeln(ans);59 end.
View Code

 

转载于:https://www.cnblogs.com/phile/p/4472951.html

你可能感兴趣的文章
网络安全之***手法计中计
查看>>
Struts2拦截器的使用 (详解)
查看>>
我的友情链接
查看>>
我的友情链接
查看>>
面向服务的架构SOA
查看>>
lnmp+lamp编译后,编译参数查看
查看>>
OEL7.2下Oracle11.2.0.4RAC部署
查看>>
nagios安装与配置
查看>>
RedHat 设置IP、网关、DNS
查看>>
MYSQL 主从复制读写分离实现
查看>>
linux更改语言
查看>>
centos7 修改mac地址
查看>>
获取Java项目根目录
查看>>
我的友情链接
查看>>
堆排序
查看>>
<script>标签的加载解析执行
查看>>
恢复rm删除的文件(ext3
查看>>
我的友情链接
查看>>
账户注销完自动登录账户,并且不需要再点击屏幕的账户头像
查看>>
【Interface&navigation】按钮(29)
查看>>