[HDU 1502][动态规划]Regular Words
来源:互联网 发布:mac配置jenkins 编辑:程序博客网 时间:2024/06/06 19:39
题目描述:
题目链接: HDU 1502
Consider words of length 3n over alphabet {A, B, C} . Denote the number of occurences of A in a word a as A(a) , analogously let the number of occurences of B be denoted as B(a), and the number of occurenced of C as C(a) .
Let us call the word w regular if the following conditions are satisfied:
A(w)=B(w)=C(w) ;
if c is a prefix of w , then A(c)>= B(c) >= C(c) .
For example, if n = 2 there are 5 regular words: AABBCC , AABCBC , ABABCC , ABACBC and ABCABC .
Regular words in some sense generalize regular brackets sequences (if we consider two-letter alphabet and put similar conditions on regular words, they represent regular brackets sequences).
Given n , find the number of regular words.
Input
There are mutiple cases in the input file.
Each case contains n (0 <= n <= 60 ).
There is an empty line after each case.
Output
Output the number of regular words of length 3n .
There should be am empty line after each case.
Sample Input
2
3
Sample Output
5
42
题目大意: 有A,B,C三种字母,每个字母有n
注意 :输入之间中间空一行,输出中间也要空一行。
题目分析:
这道动态规划题的转移方程并不难想,我们可以令f[i][j][k]记录个数,i代表A的个数,j代表B的个数,k代表C的个数,只要保证i>=j>=k。那么转移方程就是f[i][j][k]=f[i-1][j][k]+f[i][j-1][k]+f[i][j][k-1](如果在方程中i-1
但这道题的关键就在于,最后计算出来的答案到n=60时会非常大(八十几位),于是可以用类似于高精度的方法(压位)处理。对于f数组再开一维,f[i][j][k][p],答案这样记录,f[i][j][k][p+1]=f[i][j][k][p]/10000,f[i][j][k][p]%=10000。也就是说f数组记录的是答案每四位的值,p代表是第几个四位。
附代码:
#include<iomanip>#include<cmath>#include<ctime>#include<cstring>#include<string>#include<cstdlib>#include<cstdio>#include<cctype>#include<iomanip>#include<algorithm>using namespace std;const int INF=1e4;int n,f[65][65][65][30];void add(int a[],int b[]){ for(int i=0;i<=29;i++) { a[i]+=b[i]; a[i+1]+=a[i]/INF; a[i]%=INF; }}int main(){ //freopen("lx.in","r",stdin); f[0][0][0][0]=1; for(int i=1;i<=60;i++) for(int j=0;j<=i;j++) for(int k=0;k<=j;k++) { add(f[i][j][k],f[i-1][j][k]); if(j-1>=k) add(f[i][j][k],f[i][j-1][k]); if(k-1>=0) add(f[i][j][k],f[i][j][k-1]); } while(scanf("%d",&n)!=EOF) { int k=29; while(f[n][n][n][k]==0) k--;//找到最高位 for(int i=k;i>=0;i--) { if(i!=k) { int x=INF/10; while(f[n][n][n][i]<x&&x>0)//对于非最高位,存在需要填充0的情况 { printf("0"); x/=10; } if(f[n][n][n][i]!=0)printf("%d",f[n][n][n][i]); } else printf("%d",f[n][n][n][k]); } printf("\n\n"); } return 0;}
- [HDU 1502][动态规划]Regular Words
- hdu 1502 Regular Words
- hdu 1502 Regular Words
- hdu 1502 Regular Words
- 【DP】HDU-1502 Regular Words
- hdu1502 Regular Words 动态规划 高精度 打表
- Hdu 1502 Regular Words (java高精度 + DP)
- HDU 1502 Regular Words(DP + JAVA)
- HDU 1502 Regular Words(大数+dp)
- hdu 1502 Regular Words DP + 高精度 第一个java
- hdu 1502 Regular Words(java大数加法+dp)
- HDU 1502 Regular Words(打表预处理dp)
- HDU 1502 Regular Words 打表+大数相加 .
- HDU1502_Regular Words动态规划+高精度
- hdu 1502 动态规划+大数
- Leetcode Regular Expression Matching 动态规划解法
- 10. Regular Expression Matching 动态规划解法
- LeetCode : Regular Expression Matching DFS/动态规划
- 10月10日 c语言 输入星星图形 1
- Linux中的用户管理
- java之用反射实现方法(已知实体对象和实体参数)
- Tensorflow实现经典损失函数
- spring和springmvc的关系
- [HDU 1502][动态规划]Regular Words
- RN新建项目ios执行analyzer issues
- andengine 精灵的水平翻转和上下翻转
- 【模拟】Codeforces Round #438 A. Bark to Unlock 题解
- 第三与第四次作业
- 学习笔记-图像识别(Photo OCR)
- 泛型总结
- 高效工作、学习方法初探
- SuperMap iDesktop中OracleSpatial数据源新建与打开失败小结