您的位置:首页 > 运维架构

openjudge9269:Big String超级字符串 详解

2016-11-15 18:55 323 查看

9269:Big String超级字符串

查看提交统计提问

总时间限制: 10000ms 单个测试点时间限制: 1000ms 内存限制: 131072kB
描述

fish在无数次oi竞赛的狱炼之后,悟出一个真理,往往越容易的题目,陷阱越深。由此,fish创作了这道题目。 

fish首先给出两个短串A=’4567’ (4个字符), B=’123’(3个字符)。反复进行如下的操作得到一个长串C。 

(1)C=B+A (例如:A=’4567’ ,B=’123’ C=B+A=’1234567’) 

(2)A=B B=C (上述例子 A=’123’ B=’1234567’) 

请你编程找出这个长串的第n个字符。 

输入

第一行包含一个整数 n (1<=n<=10^9)
输出

仅一行,包含一个字符,表示这个长串的第n个字符。
样例输入
9

样例输出
2


显然这数据范围是很尴尬的=。=,在纸上模拟一下:

A0=4567  B0=123  -> C1=1234567

 A1=B0=123  B1=C1=1234567      ->C2=A1+B1=1234567123 

A2=B1=C1=1234567 B2=C2=1234567123  ->C3=A2+B2=C1+C2=12345671234567123

A3=B2=C2=1234567123  B3=C3=12345671234567123 ->
C4=
A3+B3=C2+C3

........

其实应该已经发现规律了:

(1)C[i]=C[i-1]+C[i-2](i>=3)

(2)每一位我们都可以在1234567这个字串中找到

(3)每一个新子串都可以看做是1234567或它的子串组成的

那么我们只需要知道第n位是1234567 中的第几位,而对这个那么长的子串究竟是什么根本没用=。=

所以我们根本没必要存具体的子串只需要存它一共有几位就行了

即:f[i]=f[i-1]+f[i-2](i>=3)

       f[1]=3;f[2]=7

所以我们只需要知道第n位是在什么时候产生的就行了,

比如说第16位,由于16>10 并且16<17 所以它是在产生到第17位的时候才知道的,

那么我们对前10位完全不感兴趣,直接16-10=6,因为它是在组成该大子串的第二个小子串中,

那么同理我们只需要知道第二个小子串中的第6位是在1234567中的第几位

.......

一直推下去一直到n<=7,即可以确定它是在1234567中的具体的位置

输出该位的数字(字符)即可

var
f :array[0..45] of int64;
n :int64;
i :longint;
s :string;
begin
read(n);s:='1234567';
f[1]:=3;f[2]:=7;
for i:=3 to 42 do f[i]:=f[i-1]+f[i-2];
for i:=1 to 42 do
if (n<=f[i+1]) and (n>f[i]) then break;

//
while (n>7) and (i>=1) do
begin
while (n<=f[i]) and (i>=1) do dec(i);
dec(n,f[i]);
end;
writeln(s
);
end.
——by Eirlys
转载请注明出处=w=

内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息
标签: