洛谷1758 BZOJ1566 管道取珠题解
2024-09-07 13:20:02
一道人类智慧的dp题
首先我们可以将∑ai^2转化为求取两次,两次一样的方案数
然后用f[i][j][k][l]表示第一个人在第一个串中取到i第二个串中取到j
第二个人在一个串中取到k第二个串中取到l的方案数
显然i+j=k+l,所以第四维可以省掉
推出方程后,可以看出f[i][j][k][l]只与f[i]与f[i-1]有关,所以可以用滚动数组优化
// luogu-judger-enable-o2
# include<iostream>
# include<cmath>
# include<algorithm>
# include<cstdio>
const int rqy = ;
const int mn = ;
char a[mn],b[mn];
int f[][mn][mn];
inline void cal(int &a,int &b)
{
a=a+b;
if(a>=rqy)
a-=rqy;
}
int n,m;
int main()
{
scanf("%d%d",&n,&m);
scanf("%s",a+);
scanf("%s",b+);
int cur=;
f[][][]=;
for(int i=;i<=n;i++,cur^=)
for(int j=;j<=m;j++)
for(int k=;k<=n;k++)
{
if(i+j-k>m || i+j-k<) continue;
if(a[i+]==a[k+])
cal(f[cur^][j][k+],f[cur][j][k]);
if(a[i+]==b[i+j-k+])
cal(f[cur^][j][k],f[cur][j][k]);
if(b[j+]==b[i+j-k+])
cal(f[cur][j+][k],f[cur][j][k]);
if(b[j+]==a[k+])
cal(f[cur][j+][k+],f[cur][j][k]);
f[cur][j][k]=;
}
printf("%d",f[cur][m][n]);
return ;
}
最新文章
- LWIP总结
- Android事件分发机制(下)
- jszs 历史管理
- [转]SpringMVC日期类型转换问题三大处理方法归纳
- 当浏览器输入url的时候发生了什么
- repo总结
- ES7前端异步玩法:async/await理解
- Python入门之函数的装饰器
- ES6 Class语法学习
- redis 持久化文章分析的很到位
- getIsDebuggable
- js 文件上传
- BZOJ 1497 [NOI2006]最大获利
- mnesia怎样改动表结构
- (I/O流)在100ms内桌面上生成一个200M大小的文件
- redis 类型、方法
- 服务器提交了协议冲突. Section=ResponseHeader Detail=CR...的解决方案总结
- HRBUST 2072 树上求最大异或路径值
- Debian 7开启ssh、telnet
- [转]Linq语法二
热门文章
- DAO设计模式总结
- mybatis学习:mybatis的环境搭建与入门
- Redis源码解析:29事务
- c++新特性实验(4)声明与定义:右值引用(C++11)
- [Array]448. Find All Numbers Disappeared in an Array
- bzoj 3743 [Coci2015]Kamp——树形dp+换根
- laravel--设置不需要csrfToken校验的接口
- 详解PPP模式下的产业投资基金运作【基金管理】
- Hibernate中的Query
- linux基础指令参数