hdu5256 序列变换 最长递增子序列

//给一个序列a , 最少改变多少元素使得其变为单调递增序列

//对于这个序列,更换的最少就是找一个最长的不需要更换的子序列

//所以就是求a[i] - i的最长递增子序列

#include<cstdio>

#include<iostream>

#include<cstring>

#include<algorithm>

using namespace std ;

const int maxn = 100010 ;

int b[maxn] ;

int find(int l , int r , int num)

{

while(l<=r)

{

int mid = (l+r) >> 1 ;

if(b[mid] <= num)

l = mid + 1 ;

else

r = mid - 1;

}

return l ;

}

int main()

{

int T ;

int n ;

int a ;

scanf("%d" , &T) ;

int cas = 0 ;

while(T--)

{

scanf("%d" , &n);

int len = 0;

for(int i = 1;i <= n;i++)

{

scanf("%d" , &a) ;

if(i == 1)

{

b[++len] = a - i ;

continue ;

}

int pos = find(1 , len , a - i) ;

b[pos] = a - i ;

if(pos > len)len++ ;

}

printf("Case #%d:\n" , ++cas) ;

printf("%d\n" , n - len) ;

}

return  0 ;

}

时间: 2024-12-08 14:32:15

hdu5256 序列变换 最长递增子序列的相关文章

最长递增子序列

问题 给定一个长度为N的数组,找出一个最长的单调自增子序列(不一定连续,但是顺序不能乱).例如:给定一个长度为6的数组A{5, 6, 7, 1, 2, 8},则其最长的单调递增子序列为{5,6,7,8},长度为4. 解法1:最长公共子序列法 这个问题可以转换为最长公共子序列问题.如例子中的数组A{5,6, 7, 1, 2, 8},则我们排序该数组得到数组A‘{1, 2, 5, 6, 7, 8},然后找出数组A和A’的最长公共子序列即可.显然这里最长公共子序列为{5, 6, 7, 8},也就是原数

最长公共子序列和最长递增子序列

1.最长公共子序列:(x和y是两个数组的长度) f(x,y) = 0                               if(x==0 || y==0) f(x-1,y-1)+1               if(A[x-1]==B[y-1]) max{f(x-1,y), f(x,y-1)} if(A[x-1]!=B[y-1]) 2.最长递增子序列 (1) 最长公共子序列法:排序后与原数组的最长公共子序列. (2) 动态规划法:(时间复杂度O(N^2)) 设长度为N的数组为{a0,a1

最长递增子序列和网易去除最少使从左向右递增又递减问题

(1)最长递增子序列问题 有两种方法:(1)动态规划方法(2)类似二分查找的方法O(nlogn) 动态规划方法: 以i结尾的序列的最长递增子序列和其[0, i - 1]“前缀”的最长递增子序列有关,设LIS[i]保存以i结尾的最长递增子序列的长度:     若i = 0,则LIS[i] = 1:     若i > 0,则LIS[i]的值和其[0, i - 1]前缀的最长递增子序列长度有关,用j遍历[0, i - 1]得到其最长递增子序列为LIS[j],对每一个LIS[j],如果序列array[j

POJ 2533 Longest Ordered Subsequence【最长递增子序列】【DP思想】

Longest Ordered Subsequence Time Limit : 4000/2000ms (Java/Other)   Memory Limit : 131072/65536K (Java/Other) Total Submission(s) : 6   Accepted Submission(s) : 1 Problem Description A numeric sequence of ai is ordered ifa1 < a2 < ... < aN. Let t

LIS(最长递增子序列)和LCS(最长公共子序列)的总结

最长公共子序列(LCS):O(n^2) 两个for循环让两个字符串按位的匹配:i in range(1, len1) j in range(1, len2) s1[i - 1] == s2[j - 1], dp[i][j] = dp[i - 1][j -1] + 1; s1[i - 1] != s2[j - 1], dp[i][j] = max (dp[i - 1][j], dp[i][j - 1]); 初始化:dp[i][0] = dp[0][j] = 0; 伪代码: dp[maxn1][ma

最长递增子序列(动态规划)

题目描述 有n个互不相同的整数an若存在一个数列bm其中对于任何1 < i < m满足bi < bi+1 且 abi < abi+1则称abn为an的一个递增子序列试求出给定序列的最长递增子序列长度 程序输入说明 本题由多组数据组成,以EOF结束 程序输出说明 对于每组数据输出一行结果,代表最长递增序列长度 程序输入样例 3 1 2 3 10 3 18 7 14 10 12 23 41 16 24 程序输出样例 3 6 1 #include<iostream> 2 #i

最长递增子序列(输出最长递增序列 及其长度)

最长递增子序列的解法有很多种,常用的有最长公共子序列法.动态规划.记录所有递增序列长度最大值的方法. 最长公共子序列法:如例子中的数组A{5,6, 7, 1, 2, 8},则我们排序该数组得到数组A‘{1, 2, 5, 6, 7, 8},然后找出数组A和A’的最长公共子序列即可.显然这里最长公共子序列为{5, 6, 7, 8},也就是原数组A最长递增子序列. 在http://blog.csdn.net/yysdsyl/article/details/4226630中有详细解释. 动态规划:参见h

最长递增子序列——解题报告

最长递增子序列--解题报告 题目描述:给定一个数组,长度为n,求出其中最长递增子序列. 分析:这题可以用动态规划求解,遍历i = 1 : n,当第i个数比前面j数大,而且前面的子序列长度加1之后,比现在的第i个子序列长的话,那么就变换.额,晦涩难懂额..看代码可以好一些. 代码如下: #include<iostream> using namespace std; // solution 1: dp int maxSubLength(int a[], int n) { int *LIS = ne

HDU 3998 Sequence (最长递增子序列+最大流SAP,拆点法)经典

Sequence Time Limit: 2000/1000 MS (Java/Others)    Memory Limit: 32768/32768 K (Java/Others) Total Submission(s): 1666    Accepted Submission(s): 614 Problem Description There is a sequence X (i.e. x[1], x[2], ..., x[n]). We define increasing subsequ