最长下降序列——中高级

Description

给你一串整数,从左到右按顺序挑出一些数字,构成严格下降序列,问最长能构成多长

如6个数4 5 2 4 2 2, 那么最长可以挑出5 4 2,长度为3

Input

首先输出T(T<=50),表示有T组数据。

每组数据:

首先输入n表示有几个数(1<n<10000)。

后面一行跟着n个整数

Output

对于每个样例输出一个数字,表示最长的长度

Sample Input


1
6
4 5 2 4 2 2

Sample Output



3

这题可以当模板用,用了单调队列的思想。

模板1:严格下降子序列

#include<iostream>
#include<stdio.h>
#include<string.h>
#include<math.h>
#include<vector>
#include<map>
#include<queue>
#include<stack>
#include<string>
#include<algorithm>
using namespace std;
int a[10006],dp[10006];
int find(int l,int r,int x)
{
	int mid;
	while(l<=r)
	{
		mid=(l+r)/2;
		if(dp[mid]>x)l=mid+1;
		else if(dp[mid]<x)r=mid-1;
		else return mid;
	}
	return l;
}

int main()
{
	int n,m,i,j,T,len,k;
	scanf("%d",&T);
	while(T--)
	{
		scanf("%d",&n);
		memset(dp,0,sizeof(dp));
		len=0;
		for(i=1;i<=n;i++){
			scanf("%d",&a[i]);
			if(len==0){
				dp[++len]=a[i];continue;
			}
			if(a[i]<dp[len]){
				dp[++len]=a[i];continue;
			}
			k=find(1,len,a[i]);
			dp[k]=a[i];
		}
		/*for(i=1;i<=len;i++){
			printf("%d ",dp[i]);
		}
		printf("\n");*/
		printf("%d\n",len);
	}
	return 0;
}

模板2:不上升子序列(非严格)

#include<iostream>
#include<stdio.h>
#include<string.h>
#include<math.h>
#include<vector>
#include<map>
#include<queue>
#include<stack>
#include<string>
#include<algorithm>
using namespace std;
int a[10006],dp[10006];
int find(int l,int r,int x)
{
	int mid;
	while(l<=r)
	{
		mid=(l+r)/2;
		if(dp[mid]>=x)l=mid+1;
		else if(dp[mid]<x)r=mid-1;
	}
	return l;
}

int main()
{
	int n,m,i,j,T,len,k;
	scanf("%d",&T);
	while(T--)
	{
		scanf("%d",&n);
		memset(dp,0,sizeof(dp));
		len=0;
		for(i=1;i<=n;i++){
			scanf("%d",&a[i]);
			if(len==0){
				dp[++len]=a[i];continue;
			}
			if(a[i]<=dp[len]){
				dp[++len]=a[i];continue;
			}
			k=find(1,len,a[i]);
			dp[k]=a[i];
		}
		for(i=1;i<=len;i++){
			printf("%d ",dp[i]);
		}
		printf("\n");
		//printf("%d\n",len);
	}
	return 0;
}
时间: 2024-10-07 23:50:05

最长下降序列——中高级的相关文章

【最长下降子序列的长度和个数】 poj 1952

转自http://blog.csdn.net/zhang360896270/article/details/6701589 这题要求最长下降子序列的长度和个数,我们可以增加数组maxlen[size](记录当前第1个点到第i个点之间的最长下降序列长度)和maxnum[size](记录1~i之间的最长下降序列个数 ),首先对于最长下降序列属于DP基础题,只要对每一个a[i]求出符合要求(a[i] < a[j])的max( maxlen[j] + 1)即可,主要难点在第二步求下降序列总数 在序列中,

Laoj P1194 [hnoi97]最长不下降序列

问题背景 动态规划入门-第13题 试题描述 设有整数序列b1,b2,b3,-,bm,若存在i1<i2<i3<-<in,且bi1<bi2<bi3<-<bin,则称 b1,b2,b3,-,bm中有长度为n的不下降序列bi1,bi2,bi3,-,bin.求序列b1,b2,b3,-,bm中所有长度(n)最大不下降子序列.例如3,18,7,14,10,12,23,41,16,24,其中3,18,23,24就是一个长度为4的不下降序列,同时也有3,7,10,12,16,

算法复习——求最长不下降序列长度(dp算法)

题目: 题目背景 161114-练习-DAY1-AHSDFZ T2 题目描述 有 N 辆列车,标记为 1,2,3,-,N.它们按照一定的次序进站,站台共有 K 个轨道,轨道遵从先进先出的原则.列车进入站台内的轨道后可以等待任意时间后出站,且所有列车不可后退.现在要使出站的顺序变为 N,N-1,N-2,-,1,询问 K 的最小值是多少. 例如上图中进站的顺序为 1,3,2,4,8,6,9,5,7,则出站的顺序变为 9,8,7,6,5,4,3,2,1. 输入格式 输入共 2 行.第 1 行包含 1 

求最长不下降序列个数

求最长不下降序列个数(jdoj-1946) 题目大意:给你一个序列,求所有最长不下降序列的个数. 注释:n(总序列长度)<10000. 想法:维护两个数组,分别表示包含这个数的最长子序列长度和达到这个长度的方案数,最后统计答案,跑两次dp即可. 最后,附上丑陋的代码....... 1 #include <iostream> 2 #include <cstdio> 3 using namespace std; 4 int dp[10010]; 5 int a[10010]; 6

【模板】求最长不下降序列 [动态规划 LIs]

求最长不下降序列 看不出来哪里还错了..... d[i]以i为结尾的最长上升子序列的长度     g[i]表示d值为i的最小状态的编号即长度为i的上升子序列的最小末尾值(d[j]=i的j值最小) liurujia's for(int i=1;i<=n;++i) g[i]=inf; for(int i=1;i<=n;++i){ int k=lower_buond(g+1,g+1+n,a[i])-g; d[i]=k; g[k]=a[i]; } 二昏好难啊..... 贴上90昏代码.... #inc

1259:【例9.3】求最长不下降序列

传送门:http://ybt.ssoier.cn:8088/problem_show.php?pid=1259 [题目描述] 设有由n(1≤n≤200) 个不相同的整数组成的数列,记为:b(1).b(2).…….b(n)且b(i)≠b(j)(i≠j),若存在i1<i2<i3<…<ie 且有b(i1)<b(i2)<…<b(ie) 则称为长度为e的不下降序列.程序要求,当原数列出之后,求出最长的不下降序列. 例如13,7,9,16,38,24,37,18,44,19,

BUY LOW, BUY LOWER_最长下降子序列

Description The advice to "buy low" is half the formula to success in the bovine stock market.To be considered a great investor you must also follow this problems' advice: "Buy low; buy lower" Each time you buy a stock, you must purcha

HDU - 6197 array array array (最长上升子序列&amp;最长下降子序列)

题意:对于一个序列,要求去掉正好K个数字,若能使其成为不上升子序列或不下降子序列,则“A is a magic array.”,否则"A is not a magic array.\n". 分析: 1.求一遍LCS,然后在将序列逆转,求一遍LCS,分别可得最长上升子序列和最长下降子序列的长度tmp1.tmp2. 2.n - tmp1 <= k或n - tmp2 <= k即可,需要去掉的去完之后,在已经是最长上升或最长下降的序列中随便去够k个就好了. #include<

POJ 1887 Testingthe CATCHER (LIS:最长下降子序列)

POJ 1887Testingthe CATCHER (LIS:最长下降子序列) http://poj.org/problem?id=3903 题意: 给你一个长度为n (n<=200000) 的数字序列, 要你求该序列中的最长(严格)下降子序列的长度. 分析:        读取全部输入, 将原始数组逆向, 然后求最长严格上升子序列就可以. 因为n的规模达到20W, 所以仅仅能用O(nlogn)的算法求.        令g[i]==x表示当前遍历到的长度为i的全部最长上升子序列中的最小序列末