您的位置:首页 > 其它

矩阵乘法求斐波那契数列

2015-08-15 10:29 295 查看

斐波那契数列的求解方法

方法一:递归

def fib(n)
if n==1 or n==2
1
else
fib(n-1)+fib(n-2)
end
end


方法二:循环

def fib(n)
if n==1 or n==2
1
else
fx,fy,index = 1,1,3
while index<= n
fx,fy,index = fy,fx+fy,index+1
end
fy
end
end


方法三:矩阵乘法(参考 斐波那契数列 矩阵求法 优化 )

斐波那契数列的递推公式为:

f(1)=1,f(2)=2,f(n)=f(n-1)+f(n-2)(n>=3)

用矩阵表示为:



进一步推导得:



$arr = [
[3524578,2178309,2178309,1346269], #基础矩阵的32次幂
[1597,987,987,610],                              #基础矩阵的16次幂
[34,21,21,13],                                       #基础矩阵的8次幂
[5,3,3,2],                                               #基础矩阵的4次幂
[2,1,1,1],                                               #基础矩阵的2次幂
[1,1,1,0]                                                    #基础矩阵的1次幂
]
def fib(k)
if k<3
return 1
else
t00,t01,t10,t11 = 1,1,1,0
a,b,c,d = t00,t01,t10,t11
k = k-2
while k>=32 do                    #对于大于等于32次幂的k转换成最多个32次幂的乘方
a = t00*$arr[0][0]+t01*$arr[0][2]
b = t00*$arr[0][1]+t01*$arr[0][3]
c = t10*$arr[0][0]+t11*$arr[0][2]
d = t10*$arr[0][1]+t11*$arr[0][3]
t00,t01,t10,t11 = a,b,c,d
k = k-32
end
mi = 4
while mi>=0 do                     #对于小于32次幂的k由大到小转换成最多个16次幂、8次幂、4次幂、2次幂、1次幂的乘方
if k>=2**mi
a = t00*$arr[5-mi][0]+t01*$arr[5-mi][2]
b = t00*$arr[5-mi][1]+t01*$arr[5-mi][3]
c = t10*$arr[5-mi][0]+t11*$arr[5-mi][2]
d = t10*$arr[5-mi][1]+t11*$arr[5-mi][3]
t00,t01,t10,t11 = a,b,c,d
k = k-2**mi
end
mi = mi-1
end
return t00
end
end


但是此代码的命中率并不是很高,这里给出我个人的代码(来自我的一篇博文:每日一道算法题004——再探矩阵
a4e5
算法求解斐波那契数列)

def getArr(k)#把k分成最少个2的n次幂的形式  如:234=2××7+2××6+2××5+2××3+2××1 记录下[7,6,5,3,1]
temp = []
while k!=0
mi = Math.log(k,2).to_i
temp<<mi
k = k-2**mi
end
temp
end
def fib(k)
if k==0
return 0
end
if k<3
return 1
else
k = k-1
arr = getArr k
t00,t01,t10,t11 = 1,1,1,0 #基础矩阵
a,b,c,d = t00,t01,t10,t11
fa,fb,fc,fd = 1,0,0,1 #初始矩阵(处理getArr==[0])也作为最终结果的矩阵
max = Math.log(k,2).to_i
bgn = 0
while bgn<=max  #计算基础矩阵的n次幂
if arr.include?bgn #如果当前的bgn在getArr[k]中,则直接将其纳入最终结果的计算
ta = fa*t00+fb*t10
tb = fa*t01+fb*t11
tc = fc*t00+fd*t10
td = fc*t01+fd*t11
fa,fb,fc,fd = ta,tb,tc,td
end
a = t00*t00+t01*t10
b = t00*t01+t01*t11
c = t10*t00+t11*t10
d = t10*t01+t11*t11
t00,t01,t10,t11 = a,b,c,d
bgn = bgn+1
end
return fa
end
end
内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息