알고리즘/BOJ

백준 2749번 피보나치 수 3

꾸준함. 2018. 2. 25. 22:58

문제 링크입니다: https://www.acmicpc.net/problem/2749

 

2749번: 피보나치 수 3

첫째 줄에 n이 주어진다. n은 1,000,000,000,000,000,000보다 작거나 같은 자연수이다.

www.acmicpc.net

앞서 http://jaimemin.tistory.com/324?category=987849에서 작성한 코드에서 자료형을 int에서 long long으로 변환하고 조건에 맞게 변환하여 문제를 푸는데 성공했습니다.


/*
F(0) = 0, F(1) = 1일 때 피보나치 수열은 F(n) = F(n - 1) + F(n - 2)이다(n >= 2)
이 때 행렬을 사용하면
┌F(n + 1) F(n)┐ = ┌1 1┐
└F(n) F(n - 1)┘ └1 0┘의 n 승
*/
#include <iostream>
#include <cstring>
using namespace std;
const int MAX = 2;
const int MOD = 1000000;
class Fibonacci
{
private:
long long fibonacci[MAX][MAX];
public:
Fibonacci()
{
memset(fibonacci, 0, sizeof(fibonacci));
}
Fibonacci &operator*(Fibonacci &f)
{
Fibonacci result;
for (int i = 0; i < MAX; i++)
{
for (int j = 0; j < MAX; j++)
{
result.fibonacci[i][j] = 0;
}
}
for (int i = 0; i < MAX; i++)
{
for (int j = 0; j < MAX; j++)
{
for (int k = 0; k < MAX; k++)
{
result.fibonacci[i][j] += (fibonacci[i][k] * f.fibonacci[k][j]) % MOD;
}
}
}
for (int i = 0; i < MAX; i++)
{
for (int j = 0; j < MAX; j++)
{
fibonacci[i][j] = result.fibonacci[i][j];
}
}
return *this;
}
long long *operator[] (int i)
{
return fibonacci[i];
}
long long answer(void)
{
return fibonacci[0][1];
}
};
Fibonacci formula, base;
void initialize(void)
{
formula[0][0] = formula[0][1] = formula[1][0] = 1;
formula[1][1] = 0;
base[0][0] = base[1][1] = 1;
base[0][1] = base[1][0] = 0;
}
Fibonacci pow(Fibonacci &f, long long n)
{
if (n == 0)
{
return base;
}
if (n == 1)
{
return formula;
}
if (n % 2)
{
return pow(f, n - 1) * f;
}
Fibonacci half = pow(f, n / 2);
return half * half;
}
int main(void)
{
ios_base::sync_with_stdio(0);
cin.tie(0);
long long N;
cin >> N;
initialize();
Fibonacci result = pow(formula, N);
cout << result.answer() % MOD << "\n";
return 0;
}
view raw .cpp hosted with ❤ by GitHub

 

 

개발환경:Visual Studio 2017

 

지적, 조언, 질문 환영입니다! 댓글 남겨주세요~

 

반응형

'알고리즘 > BOJ' 카테고리의 다른 글

백준 1309번 동물원  (0) 2018.02.28
백준 1965번 상자넣기  (0) 2018.02.26
백준 11722번 가장 긴 감소하는 부분 순열  (0) 2018.02.25
백준 11055번 가장 큰 증가 부분수열  (0) 2018.02.22
백준 11048번 이동하기  (0) 2018.02.22