xtu-1269 Similar Subsequence(dp+树状数组)
来源:互联网 发布:黑苹果mac os 11.12 编辑:程序博客网 时间:2024/06/04 01:03
Similar Subsequence
Accepted : 17 Submit : 73Time Limit : 10000 MS Memory Limit : 135536 KBSimilar Subsequence
For given sequence
s i =min{s i ,s i+1 ,…,s n } for alla i =0 ;s i =max{s i ,s i+1 ,…,s n } for alla i =1 .
Given sequence
Input
The input contains zero or more test cases and is terminated by end-of-file. For each test case:
The first line contains two integers
The second line contains
The thrid line contains
- The number of test cases does not exceed
10 . 1≤n≤20 1≤m≤500 0≤a i ≤1 1≤b i ≤m b 1 ,b 2 ,…,b m are distinct.
Output
For each case, output an integer which denotes the number of subsequences modulo
Sample Input
2 30 01 2 33 51 0 14 1 3 2 5
Sample Output
32
Note
For the first sample, all three subsequences of length
dp[i][j][x][y]表示a串中第i个元素,b串中的第j个元素,最小值为x,最大值为y时的方案数
dp[i][j][x][y]=∑dp[i-1][j'][x'][y'],[x',y']∈[x,y]
由于x,y中一定有一项等于b[j]因此可以省略一维,状态数为n*m^2
dp[i][j][k]中,
a[i]==0时,k为第i~n个被匹配的元素中最大值
a[i]==1时,k为第i~n个被匹配的元素中最小值
状态转移时用树状数组来维护:t[i][k]中i和k分别对应于dp[i][j][k]中的i和k
如果a[i]==0,sum[x]表示上下界为[1~x,k]的方案数之和
如果a[i]==1,sum[x]表示上下界为[k,1~x]的方案数之和
#include<bits/stdc++.h>#define fuck(x) cout<<'['<<x<<']';#define lson l,m,rt<<1#define rson m+1,r,rt<<1|1using namespace std;const int mod = 1e9 + 7;const int MX = 500 + 5;int a[25], b[MX], dp[25][MX][MX];int n, m;void add(int &x, int y) { x += y; if(x >= mod) x -= mod; if(x < 0) x += mod;}struct Tree { int sum[MX]; int lowbit(int x) { return x & (-x); } void update(int x, int v) { while(x) { add(sum[x], v); x -= lowbit(x); } } int query(int x) { if(x == 0) return 0; int ret = 0; while(x <= m) { add(ret, sum[x]); x += lowbit(x); } return ret; } void clear() { memset(sum, 0, sizeof(sum)); }} t[25][MX];int main() { //reopen("in.txt", "r", stdin); while(~scanf("%d%d", &n, &m)) { for(int i = 1; i <= n; i++) scanf("%d", &a[i]); for(int i = 1; i <= m; i++) scanf("%d", &b[i]); memset(dp, 0, sizeof(dp)); for(int i = 1; i <= n; i++) for(int j = 1; j <= m; j++) t[i][j].clear(); /* 初始化是个难点,如果a[1]==1,那么要设下界为最小值1 如果a[1]==0,那么要设下界为最大值m if(a[1]==1) t[1][1].update(m,1); else t[1][m].update(m,1); */ for(int i=1;i<=m;i++) dp[1][i][a[1]==1?1:m]=1; for(int i = 2; i <= n; i++) { for(int j = 1; j <= m; j++) { for(int k = 1; k <= m; k++) { dp[i][j][k] = t[i][k].query(b[j]); } for(int k = 1; k <= m; k++) { if(dp[i - 1][j][k] == 0) continue; //匹配到第i-1个数位置,上下边界为[L,R] int L = b[j], R = k; if(a[i - 1] == 1) swap(L, R); if(L > R) continue; if(a[i] == 0) { //如果a[i]==0,则下边界就是b[j],因此要枚举上边界R t[i][R].update(R, dp[i - 1][j][k]); t[i][R].update(L - 1, -dp[i - 1][j][k]); } else { //如果a[i]==1,则下边界就是b[j],因此要枚举下边界L t[i][L].update(R, dp[i - 1][j][k]); t[i][L].update(L - 1, -dp[i - 1][j][k]); } } } } int ans = 0; for(int j = 1; j <= m; j++) for(int k = 1; k <= m; k++) add(ans , dp[n][j][k]); printf("%d\n", ans); } return 0;}
- xtu-1269 Similar Subsequence(dp+树状数组)
- hdu 4991 Ordered Subsequence(dp+树状数组)
- HDU 4991 Ordered Subsequence -- DP+树状数组
- hdoj4991Ordered Subsequence【dp+离散化+树状数组】
- HDU4991 Ordered Subsequence (树状数组+dp)
- HDU4991 Ordered Subsequence (dp+树状数组+离散化)
- hdu 4991 Ordered Subsequence(树状数组优化DP)
- hdu 4991 Ordered Subsequence(DP优化—树状数组)
- HDU 4991 Ordered Subsequence(dp+树状数组)
- hdu 4991 Ordered Subsequence(树状数组+DP)
- 【HDU4991】Ordered Subsequence(离散化+dp+树状数组)
- ICPCCamp 2016 Day 3 - F Similar Subsequence (dp)
- ICPCCamp2016day4F.Similar Subsequence
- hdu5125 dp+树状数组
- hdu4521 dp+树状数组
- HDU5542(dp+树状数组)
- HDU5542(dp + 树状数组)
- hdu4991 - Ordered Subsequence (树状数组优化)
- android 触摸事件的处理与总结
- JavaScript 面向对象思想以及原型、继承
- 求pai的近似值
- oracle 游标细节引发的错误
- 勘探油田
- xtu-1269 Similar Subsequence(dp+树状数组)
- RCNN, Fast-RCNN, Faster-RCNN
- 深度学习常见的基本概念整理
- Java List集合使用方法介绍(1)
- 对树蛙培训的总结和体会
- 指针数组做函数参数
- Angular入坑指南(环境搭建)
- java数据类型补充——字符串和其他类型相加
- mariadb的网页管理