G-subsequence 1

题意

给你两个字符串\(s、t\),问\(s\)中有多少个子序列能大于\(t\)。

思路

令\(len1\)为\(s\)的子序列的长度,\(lent\)为\(t\)的长度

  1. \(len1 > lent\):枚举每一位,如果当前为不为\(0\)那么它后面的位置可以随意取,\(num = num + \binom{k}{len-1}、k\)是当前位到\(s\)的末尾剩下的位数
  2. \(len1 = lent\):暴力\(n^3\)肯定超时,所以要用\(dp\)优化

    \(dp[i][j][1]\):\(s[j]\)作为第\(i\)个数大于\(t[1\)~\(i]\)前缀的个数

    \(dp[i][j][2]\):\(s[j]\)作为第\(i\)个数等于\(t[1\)~\(i]\)前缀的个数

    • \(s[j] > t[i]\):\(dp[i][j][1] = dp[i-1][1\) ~ \(j-1][1]+dp[i-1][1\) ~ \(j-1][2]\)、\(dp[i][j][2] = 0\)

    • \(s[j] = t[i]\):\(dp[i][j][1] = dp[i-1][1\) ~ \(j-1]\)、\(dp[i][j][2] = dp[i-1][1\) ~ \(j-1][2]\)

    • \(s[j] < t[i]\):\(dp[i][j][1] = dp[i-1][1\) ~ \(j-1]\)、\(dp[i][j][2] = 0\)

  3. 用一个前缀和维护一下\(dp[i-1]\)的前缀,就可以把\(dp\)优化到\(n^2\)了

AC 代码

#include<bits/stdc++.h>
#define mes(a, b) memset(a, b, sizeof a)
using namespace std;
typedef long long ll;
const int maxn = 3e3+10;
const ll mod = 998244353;
struct A{
int num[3][maxn];
void init(){
mes(num, 0);
}
}a, b;
char s[maxn], t[maxn];
ll dp[maxn][maxn][3];
ll C[maxn][maxn];
void init(){ //组合数打表
C[0][0] = C[1][0] = C[1][1] = 1;
for(int i = 2; i < maxn;i++){
for(int j = 0; j <= i; j++){
C[i][j] = j==0?1:C[i-1][j-1]+C[i-1][j];
C[i][j] %= mod;
}
}
} int main(){
int T, n, m;
scanf("%d", &T);
init();
while(T--){
scanf("%d%d", &n, &m);
scanf("%s%s", s+1, t+1);
ll ans = 0;
a.init(); //表示dp[i-1]的前缀和
b.init(); //表示dp[i]的前缀和
for(int i = 1; i <= n-m; i++){
if(s[i] != '0')
for(int j = m; j <= n-i; j++){
ans = (ans + C[n-i][j])%mod;
}
}
for(int i = 0; i <= n; i++){ //初始化
a.num[2][i] = 1;
}
for(int i = 1; i <= m; i++){
for(int j = 1; j <= n; j++){
if(s[j] > t[i]){
dp[i][j][1] = (a.num[1][j-1]+a.num[2][j-1])%mod;
dp[i][j][2] = 0;
}
else if(s[j] == t[i]){
dp[i][j][1] = a.num[1][j-1];
dp[i][j][2] = a.num[2][j-1];
}
else{
dp[i][j][1] = a.num[1][j-1];
dp[i][j][2] = 0;
}
b.num[1][j] = (b.num[1][j-1] + dp[i][j][1])%mod;
b.num[2][j] = (b.num[2][j-1] + dp[i][j][2])%mod;
}
swap(a, b);
b.num[1][0] = b.num[2][0] = 0;
}
ans = (ans + a.num[1][n])%mod;
printf("%lld\n", ans);
}
return 0;
}

2019牛客多校第五场G-subsequence 1 DP的更多相关文章

  1. 2019牛客多校第五场 G subsequence 1 dp+组合数学

    subsequence 1 题意 给出两个数字串s,t,求s的子序列中在数值上大于t串的数量 分析 数字大于另一个数字,要么位数多,要么位数相同,字典序大,位数多可以很方便地用组合数学来解决,所以只剩 ...

  2. 2019牛客多校第五场H - subsequence 2 拓扑

    H - subsequence 2 题意 要你使用前\(m\)个小写字母构造一个长度为\(n\)的字符串 有\(m*(m-1)/2\)个限制条件: \(c_{1} .c_{2}. len\):表示除去 ...

  3. 牛客多校第五场 G subsequence 1 最长公共子序列/组合数

    题意: 给定两个由数字组成的序列s,t,找出s所有数值大于t的子序列.注意不是字典序大. 题解: 首先特判s比t短或一样长的情况. 当s比t长时,直接用组合数计算s不以0开头的,长度大于t的所有子序列 ...

  4. 2019牛客多校第五场 generator 1——广义斐波那契循环节&&矩阵快速幂

    理论部分 二次剩余 在数论中,整数 $X$ 对整数 $p$ 的二次剩余是指 $X^2$ 除以 $p$ 的余数. 当存在某个 $X$,使得式子 $X^2 \equiv d(mod \ p)$ 成立时,称 ...

  5. 2019牛客多校第五场generator2——BSGS&&手写Hash

    题目 几乎原题 BZOJ3122题解 分析 先推一波公式,然后除去特殊情况分类讨论,剩下就是形如 $a^i \equiv b(mod \ p)$ 的方程,可以使用BSGS算法. 在标准的BSGS中,内 ...

  6. 2019牛客多校第五场F maximum clique 1 最大独立集

    题意:给你n个数,现在让你选择一个数目最大的集合,使得集合中任意两个数的二进制表示至少有两位不同,问这个集合最大是多大?并且输出具体方案.保证n个数互不相同. 思路:容易发现,如果两个数不能同时在集合 ...

  7. 2019牛客多校第五场 B - generator 1 矩阵快速幂+十倍增+二进制倍增优化

    B - generator 1 题意 给你\(x_{0}.x_{1}.a.b.b.mod\),根据\(x_{i} = a*x_{i-1} + b*x_{i-2}\)求出\(x_{n}\) 思路 一般看 ...

  8. 2019牛客多校第五场B-generator 1(矩阵快速幂)

    generator 1 题目传送门 解题思路 矩阵快速幂.只是平时的矩阵快速幂是二进制的,这题要用十进制的快速幂. 代码如下 #include <bits/stdc++.h> #defin ...

  9. 2019 牛客多校第五场 B generator 1

    题目链接:https://ac.nowcoder.com/acm/contest/885/B 题目大意 略. 分析 十进制矩阵快速幂. 代码如下 #include <bits/stdc++.h& ...

随机推荐

  1. 4412 GPIO初始化

    一.GPIO的初始化 • 在内核源码目录下使用命令“ls drivers/gpio/*.o”,可以看到“gpioexynos4”被编译进了内核.通过搜索*.o文件,可以知道内核编译内哪些文件.针对的看 ...

  2. LOJ 2979 「THUSCH 2017」换桌——多路增广费用流

    题目:https://loj.ac/problem/2979 原来的思路: 优化连边.一看就是同一个桌子相邻座位之间连边.相邻桌子对应座位之间连边. 每个座位向它所属的桌子连边.然后每个人建一个点,向 ...

  3. 20175203 2018-2019 实验三 《敏捷开发与XP实践》

    20175203 2018-2019 实验三 <敏捷开发与XP实践> 实验要求 没有Linux基础的同学建议先学习<Linux基础入门(新版)><Vim编辑器> 课 ...

  4. 2018-2019-2 网络对抗技术 20165206 Exp 9 Web安全基础

    - 2018-2019-2 网络对抗技术 20165206 Exp 9 Web安全基础 - 实验任务 本实践的目标理解常用网络攻击技术的基本原理,做不少于7个题目,共3.5分.包括(SQL,XSS,C ...

  5. STM32 入门之 GPIO

    入手STM32有一段时间了,感觉刚入门时很难,无处下手,现在学到了点皮毛,写出来和大家分享一下. 首先,什么叫GPIO?这个问题,答案是我也不知道!至少目前我没有必要知道,我只要知道他其实就是51单片 ...

  6. Hooking EndScene

    Hey guys, umm i was trying to hook endscene using detours and i used a method that i hooked many oth ...

  7. JS 時間戳轉日期格式

    1.日期轉換為時間戳,(如果日期格式為時間戳,將其轉為日期類型,否則輸出傳入的數據) // 如果時間格式為時間戳,將其轉為日期 function timestampToDate(timestamp) ...

  8. centos清理缓存

    释放网页缓存(To free pagecache): echo 1 > /proc/sys/vm/drop_caches 释放目录项和索引(To free dentries and inodes ...

  9. android ndk 编译 libevent

    1. 下载 libevent 2.1.8 版本 https://github.com/libevent/libevent/releases/download/release-2.1.8-stable/ ...

  10. spring data jpa 一对多查询

    在一对多关系中,我们习惯把一的一方称之为主表,把多的一方称之为从表.在数据库中建立一对多的关系,需要使用数据库的外键约束. 什么是外键? 指的是从表中有一列,取值参照主表的主键,这一列就是外键. pa ...