正题

题目链接:https://www.luogu.com.cn/problem/P1758


题目大意

给出一个大小为\(n\)和一个大小为\(m\)的栈,每次选择一个栈弹出栈顶然后记录这个字母,求所有弹出序列的弹出方案的二次方和。

\(1\leq n,m\leq 500\)


解题思路

二次方和可以看为取出方案相同的对数。

然后就是很简单的\(dp\)了,设\(f_{i,j,k}\)表示都取出了\(i\)个,在第一个栈里分开取了\(j/k\)个,然后滚动。

时间复杂度\(O(nmn^2)\)


code

#include<cstdio>
#include<cstring>
#include<algorithm>
using namespace std;
const int N=510,P=1024523;
int n,m,f[N*2][N][N];
char s[N],t[N];
int main()
{
scanf("%d%d",&n,&m);
scanf("%s",s+1);
scanf("%s",t+1);
f[0][0][0]=1;
for(int i=1;i<=n+m;i++)
for(int j=0;j<=min(n,i);j++)
for(int k=0;k<=min(n,i);k++){
f[i&1][j][k]=0;
if(s[j]==s[k]&&j&&k)(f[i&1][j][k]+=f[~i&1][j-1][k-1])%=P;
if(s[j]==t[i-k]&&j&&i-k)(f[i&1][j][k]+=f[~i&1][j-1][k])%=P;
if(t[i-j]==s[k]&&k&&i-j)(f[i&1][j][k]+=f[~i&1][j][k-1])%=P;
if(t[i-j]==t[i-k]&&i-j&&i-k)(f[i&1][j][k]+=f[~i&1][j][k])%=P;
}
printf("%d\n",f[(n+m)&1][n][n]);
return 0;
}

最新文章

  1. 记一次与a标签相遇的小事
  2. 不能链接云服务器mysql
  3. mysql集群数据一致性校验
  4. poj1182食物链_并查集_挑战程序设计竞赛例题
  5. Java 序列化Serializable
  6. postfix启动脚本
  7. 简约的单页应用引擎:sonnyJS
  8. power designer 连接数据库提示“connection test failed”
  9. 【转载】Hadoop和大数据:60款顶级大数据开源工具
  10. [小技巧][ASP.Net MVC Hack] 使用 HTTP 报文中的 Header 字段进行身份验证
  11. ID卡常见型号
  12. ZOJ 3826 Hierarchical Notation 模拟
  13. Unity模拟龙之谷人物行走简单控制
  14. NOIP2011-普及组复赛-第一题-数字反转
  15. workday2
  16. 区间(interval)
  17. Mplayer 的编译
  18. java 高级用法整理
  19. vue .map 文件
  20. 链表排序 Sort List

热门文章

  1. GitLabRunner命令
  2. 【springboot】集成Druid 作为数据库连接池
  3. C# KeyValuePair&lt;TKey,TValue&gt; 与 Dictionary&lt;TKey,TValue&gt; 区别
  4. GIT基础篇,配置账号及命令查看以及帮助命令
  5. 聊聊 PC 端自动化最佳方案 - Pywinauto
  6. 刷题-力扣-107. 二叉树的层序遍历 II
  7. Qt5创建模态和非模态对话框
  8. k8s 存活探针(健康检查)
  9. 比培训机构还详细的 Python 学习路线,你信吗 0^0
  10. VMware NAT模式,虚机访问公网