我通过这样做找出 n 数量的斐波纳契序列:
function add(a, b) {
while (a.length < b.length) a.unshift(0);
while (a.length > b.length) b.unshift(0);
var carry = 0, sum = []
for (var i = a.length - 1; i >= 0; i--) {
var s = a[i] + b[i] + carry;
if (s >= 10) {
s = s - 10;
carry = 1;
} else {
carry = 0;
}
sum.unshift(s);
}
if (carry)
sum.unshift(carry);
return sum;
}
function fib(n) {
var f1 = [0];
var f2 = [1];
while (n--) {
var f3 = add(f1, f2)
f1 = f2;
f2 = f3;
}
return f1.join("");
}
说,我想找到1995年斐波那契数除以8时的余数。这样做,
fib(1995) % 8
然而,返回NaN
。这是fiddle,输出为console.log
。
那么如何找到1995年斐波那契数的剩余部分除以8?
答案 0 :(得分:3)
您所描述的数字理论的一个非常特殊的应用称为Pisano period:
在数论中,第n个Pisano时期,写成π(n),是Fibonacci数的序列,模n重复的时期。例如,模3的Fibonacci数是0,1,1,2,0,2,2,1,0,1,1,2,0,2,2,1等,前八个数重复,所以π(3)= 8。
n = 8的Pisano期间是12,所以你正在寻找重复序列的(1995 % 12)
'元素,所以:
0 1 1 2 3 5 0 5 5 2 7 1
^
正如评论中所提到的,每增加一对,您都可以应用模数来保持数字的可管理性:
function fib(n, mod)
{
if (n == 0) {
return 0;
} else if (n <= 2) {
return 1;
}
var current = 1,
tmp,
prev = 1;
while (n > 2) {
tmp = current;
current = (current + prev) % mod;
prev = tmp;
--n;
}
return current;
}
fib(1995, 8); // 2
答案 1 :(得分:1)
我在尝试验证IBAN号码时遇到了这个问题(欧洲银行帐户标准)。它利用一个控制号来避免错误输入账户的交易(模数97的结果总是应该是1)。
我找到了一个要点(IBAN javascript validator gist),它也能够满足你的需要。这是有用的部分(注意:divident参数必须是STRING ):
modulo = function (divident, divisor) {
var cDivident = '';
var cRest = '';
for (var i in divident ) {
var cChar = divident[i];
var cOperator = cRest + '' + cDivident + '' + cChar;
if ( cOperator < parseInt(divisor) ) {
cDivident += '' + cChar;
} else {
cRest = cOperator % divisor;
if ( cRest == 0 ) {
cRest = '';
}
cDivident = '';
}
}
cRest += '' + cDivident;
if (cRest == '') {
cRest = 0;
}
return cRest;
};
基本上,它将大数字砍成较小的数量,可以通过javascript处理。 这是一个工作小提琴:
答案 2 :(得分:0)
var cache = {};
var result = 0;
function fib_mod(number, mod) {
if( cache[number] ) return cache[number];
if( number < 3 ) result = 1 % mod; // 1st is 1, 2nd is 1 too
else result = (fib_mod(number-2, mod) + fib_mod(number-1, mod)) % mod;
cache[number] = result;
return result;
}
fib_mod(1995,8); // output is 2
JsFiddle在这里:http://jsfiddle.net/y5B7q/