[NOI2009]管道取珠 解题报告
来源:互联网 发布:啥软件下种子 编辑:程序博客网 时间:2024/04/24 16:40
这题好神啊。。
如果直接dp的话,有一个重复计算的问题很难避免。
所以这题有一个非常神的转化是可以看作是两个人在取,等于两个人取的相等方案的乘积。这样的话,做到最后当然是等于
转化之后问题就变得很简单了,我们设f(l,i,j)表示总共选了l个,其中第一个人从上管道选了i个,第二个人从上管道选了j个的方案数。
代码:
#include<cstdio>#include<iostream>using namespace std;#include<cstring>#include<cstdlib>const int N=500+5;char a[N],b[N];const int Mod=1024523;typedef long long LL;int f[2][N][N];int main(){ //cout<<(sizeof(f)>>20)<<endl; freopen("ball.in","r",stdin); //freopen("ball.out","w",stdout); int n,m; char c; scanf("%d%d%s%s",&n,&m,a+1,b+1); int state=1; f[0][0][0]=1; for(int l=1;l<=n+m;++l,state^=1){ memset(f[state],0,sizeof(f[0])); for(int i=max(0,l-m);i<=min(n,l);++i) for(int j=max(0,l-m);j<=min(n,l);++j){ if(i&&j&&a[i]==a[j])f[state][i][j]+=f[state^1][i-1][j-1]; if(l-i&&l-j&&b[l-i]==b[l-j])f[state][i][j]+=f[state^1][i][j]; if(i&&l-j&&a[i]==b[l-j])f[state][i][j]+=f[state^1][i-1][j]; if(l-i&&j&&b[l-i]==a[j])f[state][i][j]+=f[state^1][i][j-1]; f[state][i][j]%=Mod; } } printf("%d\n",f[state^1][n][n]);}
0 0
- [NOI2009]管道取珠 解题报告
- 【noi2009】管道取珠
- [NOI2009]管道取珠
- [bzoj1566][NOI2009]管道取珠
- BZOJ1566: [NOI2009]管道取珠
- bzoj1566 [NOI2009]管道取珠
- bzoj1566: [NOI2009]管道取珠
- [BZOJ1566][NOI2009]管道取珠
- BZOJ1566: [NOI2009]管道取珠
- ★【动态规划】【NOI2009】管道取珠
- BZOJ系列《[NOI2009]管道取珠》题解
- bzoj1566: [NOI2009]管道取珠 dp
- BZOJ 1566: [NOI2009]管道取珠
- 【bzoj1566】【NOI2009】【管道取珠】【dp】
- Bzoj 1566: [NOI2009]管道取珠(DP)
- BZOJ P1566[NOI2009]管道取珠
- BZOJ 1566: [NOI2009]管道取珠
- bzoj 1566 NOI 2009 管道取珠 DP 解题报告
- 数据库字段类型
- 表单事件
- java8 Stream流操作介绍
- COCI2008 解题报告
- g++: command not found的解决
- [NOI2009]管道取珠 解题报告
- 滚轮事件
- 5-24 约分最简分式 (15分)
- 框架对象事件
- servlet中load-on-startup的用法
- OC_FMDB有'深度'的DEMO
- 取消冒泡
- 选择最适合你的Linux学习方法
- javascript 常用技巧