题目链接:http://acm.csu.edu.cn/csuoj/problemset/problem?pid=1551 题意: 给出一段序列, 删除其中一段连续的子序列(或者不删), 使得剩下的序列的最长上升连续子序列最大. 题解: 1.对于要删除的的子序列而言,要么夹在答案序列中间,要么在外面(删与不删对答案都没影响).所以总体而言,答案序列被分成左右两半. 2.用SL[i]记录从左边起以a[i]为结尾的最长上升连续子序列的长度, SR记录从右边起以a[i]为开始的最长上升连续子序列的长度.…
题目链接:http://acm.csu.edu.cn/csuoj/problemset/problem?pid=1551 升级版:Uva 1471 题意: 让你求删除一段连续的子序列之后的LIS. 题解: 预处理:先求一个last[i],以a[i]为开始的合法最长上升子序列的长度.再求一个pre[i],以a[i]为结尾的合法最长上升子序列长度. 答案应该为 max(以j结束的合法最长上升子序列长度) + 以a[i]为开始的合法最长上升子序列长度. 其中j<a[i]. 1)通过树状数组维护区间最值…
题目描述 给定N个数对(xi, yi),求最长上升子序列的长度.上升序列定义为{(xi, yi)}满足对i<j有xi<xj且yi<yj. 样例输入 8 1 3 3 2 1 1 4 5 6 3 9 9 8 7 7 6 样例输出 3 题解 CDQ分治+树状数组 一道经典的二维偏序问题. 由于限制条件有2维,所以我们可以使用CDQ分治处理第一维,用树状数组维护第二维. 具体地,按照CDQ分治的思路,先处理左半部分的答案,再处理左边对右边的影响,最后再处理右半部分的答案. 处理左边对右边的影响时…
预处理last[i]表示以第i个开始,的合法后缀. pre[i]表示以第i个结尾,的合法前缀. 那么每一个数a[i],肯定是一个合法后缀last[i] + 一个合法前缀,那么合法前缀的数字要小于a[i],并且最大,bit维护小于等于val的最大值即可. #include <cstdio> #include <cstdlib> #include <cstring> #include <cmath> #include <algorithm> #inc…
1551: Longest Increasing Subsequence Again Time Limit: 2 Sec  Memory Limit: 256 MBSubmit: 75  Solved: 52 Description Give you a numeric sequence. If you can demolish arbitrary amount of numbers, what is the length of the longest increasing sequence,…
题是水题,学习一下用树状数组求LIS. 先离散化一下,注意去重:然后就把a[i]作为下标,dp[i]作为值,max作为维护的运算插进树状数组即可. 如果是上升子序列,询问(a[i] - 1):如果是不下降子序列,询问(a[i]). ; int n, m, a[maxn], b[maxn], dp[maxn], f[maxn]; void Modify(int x, int val) { for (; x <= m; x += x&-x) f[x] = max(f[x], val); } in…
题目链接   Educational Codeforces Round 39 Problem G 题意  给定一个序列,求把他变成Almost Increasing Array需要改变的最小元素个数. Almost Increasing Array为删掉至多一个元素之后可以成为严格递增子序列的数列. 这类题有个常见的套路,就是对每个元素减去下标之后求LIS. 这道题中可以删去一个元素,我们可以枚举哪个元素是被删掉的, 那么他之前的元素求LIS的时候真正的值为$a_{i} - i$,他之后的元素求…
dp[i][j]表示以a[i]结尾的长度为j的上升子序列个数. 方程:dp[i][j]=sum(dp[k][j-1]),a[k]<a[i],1<=k<i. 求解目标:sum(dp[k][m]),1<=k<=n. 三层循环枚举的话要超时,观察式子,相当于是统计前缀和,这启示我们可以用到树状数组来优化,复杂度mnlogn. 值域较大,要使用离散化. 1 #include<cstdio> 2 #include<cstring> 3 #include<a…
题意: 一个序列可能有多个最长子序列,现在问每个元素是以下三个种类的哪一类: 1.不属于任何一个最长子序列 2.属于其中某些但不是全部最长子序列 3.属于全部最长子序列 解法: 我们先求出dp1[i]表示1~i 的最长递增子序列长度, dp2[i]表示 n~i 的最长递减子序列长度(严格增减),这里我们可以用维护最大值的树状数组来解决,开始还以为要用nlogn求LIS的那种算法,当然那样应该也可以,这里元素值是1~10^5的,可以直接用树状数组,如果元素值任意的话,我们离散化一下也可以用树状数组…
题目:http://poj.org/problem?id=1631 求LIS即可,我使用了树状数组. 代码如下: #include<iostream> #include<cstdio> #include<cstring> using namespace std; int n,p,a[40005],f[40005]; int query(int x) { int ret=0; for(;x;x-=x&-x) ret=max(ret,f[x]); return re…