CLS好早的题了。。。非常经典啊。。。
 题意:给定长度为nn的串SS,求有多少个长度为mm的串TT使得LCS(S,T)LCS(S,T)分别为0,1...n0,1...n。

 我们希望能够用一个f[j][{lcs[1][j],lcs[2][j],lcs[3][j]...lcs[n][j]}]f[j][\{lcs[1][j],lcs[2][j],lcs[3][j]...lcs[n][j]\}]来表示当前状态以计算答案。
 一开始似乎会尝试直接用子序列来直接容斥。。。会发现这样很难搞,也不太对。。于是回到LCS的计算上看看有什么性质可以用。
  

LCS[i][j]=max{LCS[i−1][j],LCS[i][j−1],  [S[i]==T[j]]∗(LCS[i−1][j−1]+1)}

LCS[i][j]=\max\{LCS[i-1][j],LCS[i][j-1],[S[i] == T[j]] * (LCS[i - 1][j - 1] + 1) \}
  注意到在这个DP矩阵里面,任意相邻的两格的差至多为1,这样我们就可以用一个状压将相邻格子的差搞起来,以此表示 TT串到第jj位时的LCS状态。
  而对于状态之间的转移,可以先枚举上一行的 LCSLCS状态,算出来之后枚举当前行会和什么字符匹配,以计算出当前行的 LCSLCS状态,并得到状压的状态。简单地预处理一下就可以只枚举当前行的匹配字符来快速完成转移了。
  预处理的复杂度为 O(n2n)O(n2^n),DP复杂度为 O(m2n)O(m2^n)。
  感觉这东西要讲清楚有点麻烦呢。。。

  
丑的一B的代码:

/*I will chase the meteor for you, a thousand times over.Please wait for me, until I fade forever.Just 'coz GEOTCBRL.
*/
#include <bits/stdc++.h>
using namespace std;
#define fore(i,u)  for (int i = head[u] ; i ; i = nxt[i])
#define rep(i,a,b) for (int i = a , _ = b ; i <= _ ; i ++)
#define per(i,a,b) for (int i = a , _ = b ; i >= _ ; i --)
#define For(i,a,b) for (int i = a , _ = b ; i <  _ ; i ++)
#define Dwn(i,a,b) for (int i = ((int) a) - 1 , _ = (b) ; i >= _ ; i --)
#define fors(s0,s) for (int s0 = (s) , _S = s ; s0 ; s0 = (s0 - 1) & _S)
#define foreach(it,s) for (__typeof(s.begin()) it = s.begin(); it != s.end(); it ++)#define mp make_pair
#define pb push_back
#define pii pair<int , int>
#define fir first
#define sec second
#define MS(x,a) memset(x , (a) , sizeof (x))#define gprintf(...) fprintf(stderr , __VA_ARGS__)
#define gout(x) std::cerr << #x << "=" << x << std::endl
#define gout1(a,i) std::cerr << #a << '[' << i << "]=" << a[i] << std::endl
#define gout2(a,i,j) std::cerr << #a << '[' << i << "][" << j << "]=" << a[i][j] << std::endl
#define garr(a,l,r,tp) rep (__it , l , r) gprintf(tp"%c" , a[__it] , " \n"[__it == _])template <class T> inline void upmax(T&a , T b) { if (a < b) a = b ; }
template <class T> inline void upmin(T&a , T b) { if (a > b) a = b ; }typedef long long ll;const int maxn = 100007;
const int maxm = 200007;
const int maxs = 1 << 16;
const int mod = 1000000007;
const int inf = 0x7fffffff;
const double eps = 1e-7;typedef int arr[maxn];
typedef int adj[maxm];inline int fcmp(double a , double b) {if (fabs(a - b) <= eps) return 0;if (a < b - eps) return -1;return 1;
}inline int add(int a , int b) { return ((ll) a + b) % mod ; }
inline int mul(int a , int b) { return ((ll) a * b) % mod ; }
inline int dec(int a , int b) { return add(a , mod - b % mod) ; }
inline int Pow(int a , int b) {int t = 1;while (b) {if (b & 1) t = mul(t , a);a = mul(a , a) , b >>= 1;}return t;
}#define gc getchar
#define idg isdigit
#define rd RD<int>
#define rdll RD<long long>
template <typename Type>
inline Type RD() {char c = getchar(); Type x = 0 , flag = 1;while (!idg(c) && c != '-') c = getchar();if (c == '-') flag = -1; else x = c - '0';while (idg(c = gc()))x = x * 10 + c - '0';return x * flag;
}
inline char rdch() {char c = gc();while (!isalpha(c)) c = gc();return c;
}
#undef idg
#undef gc// beginning#define shl(x) (1 << (x))const char ch[] = {'A' , 'C' , 'G' , 'T'};int n , m , all;
int bcnt[maxs] , trans[maxs][4];
int f[2][maxs];char S[16];void input() {scanf("%s" , S + 1);n = strlen(S + 1) , m = rd();all = shl(n);
}inline void init_trans() {static int pre[16] , cur[16];For (s , 0 , all) {if (s)bcnt[s] = bcnt[s >> 1] + (s & 1);For (i , 0 , n) pre[i + 1] = pre[i] + (s >> i & 1);rep (c , 0 , 3) {int t = 0;cur[0] = 0;rep (i , 1 , n) {cur[i] = max(cur[i - 1] , pre[i]);if (S[i] == ch[c]) upmax(cur[i] , pre[i - 1] + 1);t |= (cur[i] - cur[i - 1]) << (i - 1);}trans[s][c] = t;}}
}#define upd(a,b) a = add(a , b)void solve() {int cur = 0 , nxt = 1;init_trans();memset(f[cur] , 0 , all << 2);f[0][0] = 1;For (i , 0 , m) {memset(f[nxt] , 0 , all << 2);For (s , 0 , all) if (f[cur][s]) For (c , 0 , 4)upd(f[nxt][trans[s][c]] , f[cur][s]);cur ^= 1 , nxt ^= 1;}static int ans[16];rep (i , 0 , n) ans[i] = 0;For (s , 0 , all)upd(ans[bcnt[s]] , f[cur][s]);rep (i , 0 , n) printf("%d\n" , ans[i]);
}int main() {#ifndef ONLINE_JUDGEfreopen("data.txt" , "r" , stdin);#endifrep (T , 1 , rd()) {input();solve();}return 0;
}

【bzoj 3864】Hero meets devil - DP套DP相关推荐

  1. bzoj 3864: Hero meet devil [dp套dp]

    3864: Hero meet devil 题意: 给你一个只由AGCT组成的字符串S (|S| ≤ 15),对于每个0 ≤ .. ≤ |S|,问 有多少个只由AGCT组成的长度为m(1 ≤ m ≤ ...

  2. BZOJ 3864: Hero meet devil (从dp性质实现dp套dp)

    题意:求长度为m的,字符集大小为4的,字符串,中,与字符串S(|S|<=15)的最长公共子序列长度=i的字符串数量.i∈0→∣S∣i \ \in 0 \to |S|i ∈0→∣S∣ 发现这个状态 ...

  3. [XSY] 相似(DP套DP)

    相似 在看这道题前,有必要先看一下DP套DP的入门题[uoj3864]Hero meet devil,附上两篇写得不错的题解: https://blog.csdn.net/Ike940067893/a ...

  4. dp套dp(动态规划)

    dp套dp 这是一个对于一类动态规划的计数问题的处理方法,问题常常是如果形式确定就可以直接dp,但是现在却要求满足某个要求的所有方案数,一般的处理方法就是一维负责增量构造,其他维度用来表示内部dp状态 ...

  5. hdu4899 dp套dp

    题意:只含字母ATGC,  给定一个S串,长度小于等于15,构造满足LCS(S,T)=X的T串,求这样的T串的个数,0<=X<=|S| 网上有一堆题解,但大多数都讲得根本让人无法理解 以下 ...

  6. 【luogu P4590】游园会(DP套DP)

    游园会 题目链接:luogu P4590 题目大意 给你一个匹配字符串,然后问你对于所有的长度为 n 的字符串,满足不存在 NOI 的子串,跟匹配字符串 LCS 为 x 的有多少个,对于每个 x 都求 ...

  7. #3864. Hero meet devil dp套dp + 状压 + 状态机

    传送门 文章目录 题意: 思路: 题意: 给你一个只包含ACGTACGTACGT的串sss,再给你一个mmm,第iii行输出有多少个长度为mmm且只包含ACGTACGTACGT的串与sss的lcslc ...

  8. [ZJOI2019]麻将 题解(dp 套 dp)

    文章目录 前言 题面 题解 坑点 代码 前言 做这道题的想法从看到这场比赛的 T2 的题解时就开始了.3.1 ~ 3.16 号,共 16 天的历程,我才终于搞出来这道题.在这 16 天里,我每天都要花 ...

  9. [BZOJ 3864][HDU 4899]Hero meet devil(DP套DP)

    题意 给你一个只由AGCT组成的字符串S(|S|≤15),对于每个1≤i≤|S| 询问有多少个只由AGCT组成的长度为m(1≤m≤1000)的字符串T,使得LCS(S,T)=i. |S|<=15 ...

  10. HDU 4899 Hero meet devil (状压DP, DP预处理)

    题意:给你一个基因序列s(只有A,T,C,G四个字符,假设长度为n),问长度为m的基因序列s1中与给定的基因序列LCS是0,1......n的有多少个? 思路:最直接的方法是暴力枚举长度为m的串,然后 ...

最新文章

  1. 【2018-01-22】HTML-表单及表单元素
  2. C语言 整型变量的输入和输出
  3. android XMl 解析神奇xstream 一: 解析android项目中 asset 文件夹 下的 aa.xml 文件
  4. ActiveMQ(07):ActiveMQ结合Spring开发--建议
  5. 读取文件卡顿_CPU占用100%,电脑卡顿原来可以这样解决!多任务操作也运行如飞...
  6. XJOI 3864 农村连接城市
  7. generator tar.gz file in windows
  8. ValueError: operands could not be broadcast together with shapes (3000,20) (20,20)
  9. 主流GPS方案供应商大盘点
  10. 索尼Xperia XZ1 Compact刷机,解锁BL,刷Twrp Recovery和Root教程
  11. C#调用三菱的MX Component控件与三菱PLC进行通讯
  12. 51单片机(AT89S52)设计简单计算器(4位加减乘除)
  13. 网红框架FastAPI能否补足python饱受诟病的速度
  14. navicat报错 Access violation at address in module ‘navicat.exe‘
  15. Ext grid columns隐藏列
  16. OSDI2020:Delos中的虚拟共识
  17. 阿里面试官问我:如何设计秒杀系统?我给出接近满分的回答
  18. 使用JDBC操作数据库的六部曲
  19. 【智能路由器】openwrt创建用户软件包
  20. c语言六位抢答器课程设计,基于c语言单片机8位竞赛抢答器设计课程设计.docx

热门文章

  1. Tilera--100核cpu
  2. 【GD32F310开发板试用】利用I2C接口通过温湿度传感器HDC1080读取当前环境温湿度
  3. 数字化底层逻辑揭秘!探寻地产工程行业发展新范式
  4. java 检测ip网速_网站节点测速,网站节点测速,测试网站的真实打开时间
  5. 苹果手机备份数据到电脑什么位置 iPhone备份到电脑上的东西在哪里
  6. docker run参数-v的rw、ro详解
  7. mysql统计每个学生的选课门数_SQL一个查询中包含两个聚集函数怎么弄啊例如,查询每名学生的选课门数和平均成绩怎么弄啊...
  8. 在一夜暴富之前,我先一夜秃了头
  9. allgro pcb铜皮编辑_Allegro设计PCB基础知识:快捷键设置、铜皮处理、DC-DC布局布线、电源分割等等...
  10. docker使用阿里云的镜像加速器的地址