原题链接: http://acm.hdu.edu.cn/showproblem.php?pid=1005
很早前就注册过大名鼎鼎的杭电acm的账号,但是一直没有提交过代码。昨天在论坛上看到有人求java版本的1005代码,所以就试着写了一下:
首先,看题目,貌似很简单的一个问题,直接代入公式就行了,觉得有些不可思议,但是还是写了最初版本的代码,如下:
想要提高运行时间,自然要优化代码,但是在最初版本的代码上,试着优化了几次,皆是超时,这时候从网上查了下思路,才意识到没有注意到mod运算导致的问题。
因为f(n)的结果是模7的,那么f(n)的结果只可能在{0,1,2,3,4,5,6,}中,这样f(n)与f(n-1)的结果只可能是7*7 = 49种,合理利用周期性,便可以大大提高程序运行时间。
最终AC的代码如下,Rank 280,我不是搞算法的,懒得再优化了:
Problem Description
A number sequence is defined as follows:
f(1) = 1, f(2) = 1, f(n) = (A * f(n - 1) + B * f(n - 2)) mod 7.
Given A, B, and n, you are to calculate the value of f(n).
f(1) = 1, f(2) = 1, f(n) = (A * f(n - 1) + B * f(n - 2)) mod 7.
Given A, B, and n, you are to calculate the value of f(n).
Input
The input consists of multiple test cases. Each test case contains 3 integers A, B and n on a single line (1 <= A, B <= 1000, 1 <= n <= 100,000,000). Three zeros signal the end of input and this test case is not to be processed.
Output
For each test case, print the value of f(n) on a single line.
Sample Input
1 1 3 1 2 10 0 0 0
Sample Output
2 5
很早前就注册过大名鼎鼎的杭电acm的账号,但是一直没有提交过代码。昨天在论坛上看到有人求java版本的1005代码,所以就试着写了一下:
首先,看题目,貌似很简单的一个问题,直接代入公式就行了,觉得有些不可思议,但是还是写了最初版本的代码,如下:
package algorithms;
import java.math.BigInteger;
import java.util.Scanner;
public class Main {
public static void main(String[] args) {
Scanner in = new Scanner(System.in);
int a, b;
int n;
while (in.hasNext()) {
a = in.nextInt();
b = in.nextInt();
n = in.nextInt();
// 1 <= A, B <= 1000, 1 <= n <= 100,000,000
if (a < 1 & a > 1000 & b < 1 & b > 1000 & b < 1 & a > 100000000)
System.exit(0);
if (a == 0 & b == 0 & n == 0)
System.exit(0);
int count = n - 2;
int i = 0;
BigInteger f[] = new BigInteger[2];
f[0] = BigInteger.valueOf(1);
f[1] = BigInteger.valueOf(1);
while (i < count) {
BigInteger tmp = (f[0].multiply(BigInteger.valueOf(a)).add(f[1]
.multiply(BigInteger.valueOf(b)))).remainder(BigInteger
.valueOf(7));
f[1] = f[0];
f[0] = tmp;
i++;
}
System.out.println(f[0]);
}
in.close();
}
}
在本地测试了Sample中的几组数据,结果皆没有问题,然后就去提交code,结果没有期望的ac,而是
Time Limit Exceeded,这时候才意识到这个问题不是考察能不能得出结果,而是考察代码的效率。
想要提高运行时间,自然要优化代码,但是在最初版本的代码上,试着优化了几次,皆是超时,这时候从网上查了下思路,才意识到没有注意到mod运算导致的问题。
因为f(n)的结果是模7的,那么f(n)的结果只可能在{0,1,2,3,4,5,6,}中,这样f(n)与f(n-1)的结果只可能是7*7 = 49种,合理利用周期性,便可以大大提高程序运行时间。
最终AC的代码如下,Rank 280,我不是搞算法的,懒得再优化了:
import java.util.Scanner;
public class Main{
public static void main(String[] args) {
Scanner in = new Scanner(System.in);
int a, b;
int n;
while (in.hasNext()) {
a = in.nextInt();
b = in.nextInt();
n = in.nextInt();
// 1 <= A, B <= 1000, 1 <= n <= 100,000,000
if (a < 1 & a > 1000 & b < 1 & b > 1000 & b < 1 & a > 100000000)
System.exit(0);
if (a == 0 & b == 0 & n == 0)
System.exit(0);
int f[] = new int[50];
for (int i = 1; i < 50; i++) {
if (i == 1 || i == 2) {
f[i] = 1;
} else {
f[i] = (a * f[i - 1] + b * f[i - 2]) % 7;
}
}
System.out.println(f[n % 49]);
}
in.close();
}
}