百度之星1005 序列变换(lis)

来源:互联网 发布:mac卸载程序 残留图标 编辑:程序博客网 时间:2024/06/06 04:00

序列变换

Time Limit: 20 Sec  Memory Limit: 256 MB

题目连接

http://bestcoder.hdu.edu.cn/contests/contest_showproblem.php?cid=601&pid=1003

题目描述

我们有一个数列A1,A2...An,你现在要求修改数量最少的元素,使得这个数列严格递增(严格递增即相邻元素不存在相等的情况)。其中无论是修改前还是修改后,每个元素都必须是整数。 请输出最少需要修改多少个元素。

输入

第一行输入一个T(1≤T≤10)T (1 \leq T \leq 10)T(1T10),表示有多少组数据

每一组数据:

第一行输入一个N(1≤N≤105)N (1 \leq N \leq 10^5)N(1<N<100000)表示数列的长度

第二行输入N个数A1,A2,...,AnA_1, A_2, ..., A_n,每一个数列中的元素都是正整数而且不超过1e6.

输出

对于每组数据,先输出一行

Case #i:

然后输出最少需要修改多少个元素。

样例输入

221 1032 5 4

样例输出

Case #1:0Case #2:1

要想做这道题需要把每组数据里的每个元素减去下标,然后再求n-最长上升子序列长度.

#include<stdio.h>#include<string.h>int a[100100],b[100100],len;int fun(int i){int l,r,mid;l=1;r=len;while(l<=r){mid=(l+r)/2;if(a[i]>=b[mid])l=mid+1;else r=mid-1;}return l;}int main(){int t,i,k=1;scanf("%d",&t);while(t--){int n;memset(a,0,sizeof(a));memset(b,0,sizeof(b));scanf("%d",&n);    for(i=1;i<=n;i++)    {    scanf("%d",&a[i]);    a[i]-=i;}//下面是求最长上升子序列的长度 b[1]=a[1];len=1;for(i=2;i<=n;i++){if(b[len]<=a[i]){b[++len]=a[i];}else {int pos=fun(i);b[pos]=a[i];}}printf("Case #%d:\n",k++);printf("%d\n",n-len);}return 0;} 


 

0 0
原创粉丝点击