hdoj 4062 Queuing 【矩阵快速幂优化递推公式】
2015-08-31 16:43
375 查看
QueuingTime Limit: 10000/5000 MS (Java/Others) Memory Limit: 32768/32768 K (Java/Others)Total Submission(s): 3609 Accepted Submission(s): 1629 Problem Description Queues and Priority Queues are data structures which are known to most computer scientists. The Queue occurs often in our daily life. There are many people lined up at the lunch time. Now we define that ‘f’ is short for female and ‘m’ is short for male. If the queue’s length is L, then there are 2L numbers of queues. For example, if L = 2, then they are ff, mm, fm, mf . If there exists a subqueue as fmf or fff, we call it O-queue else it is a E-queue. Your task is to calculate the number of E-queues mod M with length L by writing a program. Input Input a length L (0 <= L <= 10 6) and M. Output Output K mod M(1 <= M <= 30) where K is the number of E-queues with length L. Sample Input 3 8 4 7 4 8 Sample Output 6 2 1 |
思路:这道题需要先推出公式f(L) = f(L-1) + f(L-3) + f(L-4)。然后同求斐波那契数列的方式,构造矩阵,下面就是矩阵快速幂了。
公式推导:
我们考虑L长序列的最后一位字符C1
一:C1 = m,我们不用考虑前面L-1字符,直接有方案数f(L-1);
二:C1 = f,我们需要考虑L长序列的倒数第二个字符C2
1,C2 = m,因为末尾序列可能存在fmf的情况,我们需要考虑L长序列的倒数第三个字符C3
(1) C3 = m,得到末尾三个字符mmf,我们不用考虑mmf前面的字符,有方案数f(L-3);
(2) C4 = f,得到末尾三个字符fmf,不是E-序列。
2,C2 = f,因为末尾序列可能存在fff的情况,我们需要考虑L长序列的倒数第三个字符C3
(1) C3 = m,得到末尾三个字符mff,因为末尾序列可能存在fmff的情况,我们考虑倒数第四个字符C4
One C4 = m,得到末尾序列mmff,我们不用考虑mmff前面的字符,有方案数f(L-4);
TwoC4 = f,得到末尾序列fmff,不是E-序列。
(2) C4 = f,得到末尾三个字符fff,不是E-序列。
这样总方案数f(L) = f(L-1) + f(L-3) + f(L-4)。
下面就是构造矩阵了,给个图示
初始矩阵 F矩阵
构造矩阵后,求出初始矩阵的L-3次幂,最后再与F矩阵相乘得到结果矩阵Ans。最后的答案就是Ans[0]。
这里说的是L>3的情况,至于L <= 3的情况只需要注意L = 0时结果是0就行了。
AC代码:
#include <cstdio> #include <cstring> #include <algorithm> #define MAXN 6 #define LL long long using namespace std; struct Matrix { int a[MAXN][MAXN]; int r, c; }; Matrix ori, res; int F[5];//F矩阵 int Ans[5];//结果矩阵 void init() { //构造矩阵 ori.r = ori.c = 4; memset(ori.a, 0, sizeof(ori.a)); ori.a[0][0] = ori.a[0][2] = ori.a[0][3] = 1; ori.a[1][0] = ori.a[2][1] = ori.a[3][2] = 1; //构造单位矩阵 res.r = res.c = 4; memset(res.a, 0, sizeof(res.a)); res.a[0][0] = res.a[1][1] = res.a[2][2] = res.a[3][3] = 1; //构造F矩阵 F[0] = 6, F[1] = 4, F[2] = 2, F[3] = 1; } Matrix muitl(Matrix x, Matrix y, int m) { Matrix z; memset(z.a, 0, sizeof(z.a)); z.r = x.r; z.c = y.c; for(int i = 0; i < x.r; i++) { for(int k = 0; k < x.c; k++) { if(x.a[i][k] == 0) continue; for(int j = 0; j < y.c; j++) z.a[i][j] = (z.a[i][j] + (x.a[i][k] * y.a[k][j]) % m) % m; } } return z; } void Matrix(int n, int m) { while(n) { if(n & 1) res = muitl(ori, res, m); ori = muitl(ori, ori, m); n >>= 1; } } void solve(int n, int m) { Matrix(n, m);//矩阵的n次幂 对m取余 memset(Ans, 0, sizeof(Ans)); for(int i = 0; i < res.r; i++) { for(int k = 0; k < res.c; k++) Ans[i] = (Ans[i] + res.a[i][k] * F[k]) % m; } printf("%d\n", Ans[0]); } int main() { int L, M; while(scanf("%d%d", &L, &M) != EOF) { Ans[0] = 0, Ans[1] = 2, Ans[2] = 4, Ans[3] = 6; if(L <= 3) { printf("%d\n", Ans[L] % M); continue; } init();//构造矩阵 solve(L-3, M); } return 0; }
相关文章推荐
- UITableView-------模型的使用
- 你给我解析清楚,都有了CALayer了,为什么还要UIView
- 用Arduino监控的自动咖啡壶
- Android线程---UI线程和非UI线程之间通信
- UIEvent - 1
- 77 NSMutableURLRequest常用设置 GET和POST比较 发送JSON给服务器
- 阿里DruidDataSource配置(druid)
- 疯狂ios讲义之选择器(UIPickerView)
- 一个实用的android框架(二)—— UI
- iOS_UI_5_user-defined(自定义)View
- UINavigationController官方文档学习笔记
- poj 1679 The Unique MST
- DataGridView Index -1 does not have a value 错误
- SoapUI 引用第三方jar包和引用Groovy脚本
- break 退出循环 continue 提前进入下一轮循环 while的特殊用法
- UINavigationController详解
- Xamarin iOS UIAlertView
- Ehcache配置时出错- Another unnamed CacheManager already exists in the same VM. Please provide unique name
- ExtJs 集成UEditor and KindEditor
- 解决报错:A potentially dangerous Request.Form value was detected from the client