POJ 3070 —— Fibonacci 【矩阵快速幂】

Fibonacci

Time Limit: 1000MS   Memory Limit: 65536K
Total Submissions: 12190   Accepted: 8651

Description

In the Fibonacci integer sequence, F0 = 0, F1 = 1, and Fn = Fn − 1 + Fn − 2 for n ≥ 2. For example, the first ten terms of the Fibonacci sequence are:

0, 1, 1, 2, 3, 5, 8, 13, 21, 34, …

An alternative formula for the Fibonacci sequence is

.

Given an integer n, your goal is to compute the last 4 digits of Fn.

Input

The input test file will contain multiple test cases. Each test case consists of a single line containing n (where 0 ≤ n ≤ 1,000,000,000). The end-of-file is denoted by a single line containing the number −1.

Output

For each test case, print the last four digits of Fn. If the last four digits of Fn are all zeros, print ‘0’; otherwise, omit any leading zeros (i.e., print Fn mod 10000).

Sample Input

0
9
999999999
1000000000
-1

Sample Output

0
34
626
6875
#include <cstdio>
#include <iostream>
#include <vector>
#include <assert.h>
using namespace std;

const int MOD = (int)1e4;

struct Mat {
    vector<vector<int> > m;
    Mat() {}
    Mat(int a, int b) {
        m.resize(a);
        for(int i=0; i<m.size(); i++) {
            m[i].resize(b);
        }
    }
};

Mat operator * (const Mat& a, const Mat& b) {
    assert(a.m[0].size() == b.m.size());
    Mat c(a.m.size(), b.m[0].size());
    for(int i=0; i<a.m.size(); i++) {
        for(int j=0; j<b.m[0].size(); j++) {
            c.m[i][j] = 0;
            for(int k=0; k<b.m.size(); k++) {
                c.m[i][j] = (c.m[i][j] + a.m[i][k] * b.m[k][j] % MOD) % MOD;
            }
        }
    }
    return c;
}

Mat operator ^ (Mat a, int k) {
    assert(a.m.size() == a.m[0].size());
    Mat c(a.m.size(), a.m.size());

    for(int i=0; i<a.m.size(); i++) {
        for(int j=0; j<a.m.size(); j++) {
            c.m[i][j] = (i==j);
        }
    }

    while(k) {
        if(k&1) {
            c = c * a;
        }
        a = a * a;
        k>>=1;
    }
    return c;
}

int main ()
{
    int n;
    Mat a(2,2), b(2,1);
    a.m[0][0]=a.m[1][0]=a.m[0][1]=1;
    a.m[1][1]=0;

    b.m[0][0]=1;
    b.m[1][0]=0;

    while(scanf("%d", &n) != EOF && n != -1) {
        if(n==0)    printf("%d\n", b.m[1][0]);
        else if(n==1)    printf("%d\n", b.m[0][0]);
        else {
            Mat ans = (a^(n-1)) * b;
            printf("%d\n", ans.m[0][0]);
        }
    }

    return 0;
}
时间: 2024-11-05 20:03:44

POJ 3070 —— Fibonacci 【矩阵快速幂】的相关文章

poj 3070 Fibonacci (矩阵快速幂求斐波那契数列的第n项)

题意就是用矩阵乘法来求斐波那契数列的第n项的后四位数.如果后四位全为0,则输出0,否则 输出后四位去掉前导0,也...就...是...说...输出Fn%10000. 题目说的如此清楚..我居然还在%和/来找后四位还判断是不是全为0还输出时判断是否为0然后 去掉前导0.o(╯□╰)o 还有矩阵快速幂的幂是0时要特判. P.S:今天下午就想好今天学一下矩阵乘法方面的知识,这题是我的第一道正式接触矩阵乘法的题,欧耶! #include<cstdio> #include<iostream>

poj 3070 Fibonacci 矩阵快速幂

题目链接:http://poj.org/problem?id=3070 In the Fibonacci integer sequence, F0 = 0, F1 = 1, and Fn = Fn − 1 + Fn − 2 for n ≥ 2. For example, the first ten terms of the Fibonacci sequence are: 0, 1, 1, 2, 3, 5, 8, 13, 21, 34, … An alternative formula for t

poj 3070 Fibonacci (矩阵快速幂乘/模板)

题意:给你一个n,输出Fibonacci (n)%10000的结果 思路:裸矩阵快速幂乘,直接套模板 代码: #include <cstdio> #include <cstring> #include <iostream> using namespace std; typedef long long ll; const int N=2,M=2,P=2; const int MOD=10000; struct Matrix { ll m[N][N]; }; Matrix

POJ 3070 Fibonacci(矩阵快速幂)

Description In the Fibonacci integer sequence, F0 = 0, F1 = 1, and Fn = Fn ? 1 + Fn ? 2 for n ≥ 2. For example, the first ten terms of the Fibonacci sequence are: 0, 1, 1, 2, 3, 5, 8, 13, 21, 34, - An alternative formula for the Fibonacci sequence is

POJ 3070 Fibonacci 矩阵快速求法

就是Fibonacci的矩阵算法,不过增加一点就是因为数字很大,所以需要取10000模,计算矩阵的时候取模就可以了. 本题数据不强,不过数值本来就限制整数,故此可以0ms秒了. 下面程序十分清晰了,因为分开了几个小函数了,适合初学者参考下. #include <stdio.h> const int MOD = 10000; void mulOneMatrix(int F[2][2]) { int a = F[0][0]; int b = F[1][0]; F[0][0] = (a+b)%MOD

3070 Fibonacci 矩阵快速幂

#include<stdio.h> #include<string.h> #include<algorithm> using namespace std; const int m=10000; int fib(int n) { int t[2][2]={1,1,1,0}; int p[2][2]; int a[2][2]={1,0,0,1}; int i,j,k; while(n) { if(n%2==1) { for(i=0;i<2;i++) for(j=0;j

[POJ 3734] Blocks (矩阵快速幂、组合数学)

Blocks Time Limit: 1000MS   Memory Limit: 65536K Total Submissions: 3997   Accepted: 1775 Description Panda has received an assignment of painting a line of blocks. Since Panda is such an intelligent boy, he starts to think of a math problem of paint

POJ Fibonacci 3070【矩阵快速幂】

Fibonacci Time Limit: 1000MS   Memory Limit: 65536K Total Submissions: 10931   Accepted: 7770 Description In the Fibonacci integer sequence, F0 = 0, F1 = 1, and Fn = Fn ? 1 + Fn ? 2 for n ≥ 2. For example, the first ten terms of the Fibonacci sequenc

HDU1588-Gauss Fibonacci(矩阵快速幂+等比数列二分求和)

题目链接 题意:g(x) = k * x + b.f(x) 为Fibonacci数列.求f(g(x)),从x = 1到n的数字之和sum,并对m取模. 思路: 设A = |(1, 1),(1, 0)| sum = f(b) + f(k + b) + f(2k + b)...+f((n-1)k + b) (f(x) 为Fibonacci数列) sum = A^b + A^(k + b) + A^(2k + b)...+ A^((n-1)k + b) sum = A^b(1 + A^k + A^2k

POJ 3734 Blocks (矩阵快速幂)

题目链接:http://poj.org/problem?id=3734 <挑战程序设计竞赛>202页.与单纯的用递推式与矩阵快速幂求第N项不同,设染到第i个方块为止,红绿都是偶数的方案数目为a,红绿恰有一个是偶数方案数目为b,红绿都是奇数方案数目为c, 则: a[i+1] = 2 * a[i] + b[i] b[i+1] = 2 * a[i]+2 * b[i]+2 * c[i] c[i+1] = b[i] + 2 * c[i] 之后构建3*3矩阵求解 代码: 1 typedef vector&