无限序列
Description
我們按以下方式產(chǎn)生序列: 1、 開始時序列是: “1” ; 2、 每一次變化把序列中的 “1” 變成 “10” ,”0” 變成 “1”。 經(jīng)過無限次變化,我們得到序列”1011010110110101101…”。 總共有 Q 個詢問,每次詢問為:在區(qū)間A和B之間有多少個1。 任務(wù):寫一個程序回答Q個詢問
Input
第一行為一個整數(shù)Q,后面有Q行,每行兩個數(shù)用空格隔開的整數(shù)a, b。
Output
共Q行,每行一個回答
Sample Input
1
2 8
Sample Output
4
Data Constraint
【數(shù)據(jù)范圍】
1 <= Q <= 5000
1 <= a <= b < 2^63
分析
序列——————長度——1的個數(shù)
1————————1————1
10————————2————1
101———————3————2
10110——————5—————3
10110101—————8————5
1011010110110——13————8
………………………..
可以很容易的發(fā)現(xiàn),長度和1的個數(shù)都是斐波那契數(shù)列
然后每一個序列s[i]=s[i-1]+s[i-2]
然后可以想到用遞歸(然而我并沒有想到)。
對于每一個序列s[i],我們都可以把它分割成s[i-1]和s[i-2],然后s[i-2]繼續(xù)分割成s[(i-2)-1]和s[(i-2)-2]……最后s被分成很多個長度和1的個數(shù)在變化之內(nèi)的序列,這些序列1的個數(shù)相加,ans[b]-ans[a-1]即答案。
注意數(shù)據(jù)有點大,可以qword(無符號的整型0~2^64-1)
程序:
const maxn=92; var n,i:longint; a,b:qword; t,f:array[0..105]of qword;function dfs(x:qword;i:longint):qword; beginif (x=0) then exit(0);if (x=t[i]) then exit(f[i]);if x>t[i-1] then dfs:=dfs(x-t[i-1],i-2)+f[i-1] else dfs:=dfs(x,i-1); end;beginreadln(n);t[0]:=1;t[1]:=1;f[0]:=0;f[1]:=1;for i:=2 to maxn dobegint[i]:=t[i-1]+t[i-2];f[i]:=f[i-1]+f[i-2];end;for i:=1 to n dobeginreadln(a,b);writeln(dfs(b,maxn)-dfs(a-1,maxn));end; end.轉(zhuǎn)載于:https://www.cnblogs.com/YYC-0304/p/9500001.html
總結(jié)