UVa 497 - Strategic Defense Initiative

题目:最大上升子序列,输出一组解。

分析:dp,LIS。数据较小 O(n^2)算法即可。

设以第i个数字作为最大上升子序列中的最后一个数的长度为 f(i),则有转移方程:

f(i)= max(f(j)) { 0=< j < i  && data[j] < data[i] };

用一个数组记录前驱,递归输出即可。

说明:注意输出格式有点纠结。

#include <iostream>
#include <cstdlib>
#include <cstring>
#include <cstdio>

using namespace std;

char buf[256];
int  data[10000];
int  dp[10000];
int  front[10000];

void output( int d, int s )
{
	if ( front[s] >= s )
		printf("Max hits: %d\n",d+1);
	else
		output( d+1, front[s] );
	printf("%d\n",data[s]);
}

int main()
{
	int n;
	while (~scanf("%d",&n)) {
		getchar();
		getchar();
		while ( n -- ) {
			char ch;
			int count = 0;
			while (gets(buf) && buf[0])
				data[count ++] = atoi(buf);
			for ( int i = 0 ; i < count ; ++ i ) {
				dp[i] = 1;
				front[i] = i;
				for ( int j = 0 ; j < i ; ++ j )
					if ( data[i] > data[j] && dp[i] < dp[j]+1 ) {
						dp[i] = dp[j]+1;
						front[i] = j;
					}
			}

			int max = 0;
			for ( int i = 1 ; i < count ; ++ i )
				if ( dp[i] > dp[max] )
					max = i;

			if ( count )
				output( 0, max );
			else printf("Max hits: 0\n");
			if ( n ) printf("\n");
		}
	}
	return 0;
}
时间: 2024-08-04 22:58:23

UVa 497 - Strategic Defense Initiative的相关文章

UVa 2038 - Strategic game(二分图最小顶点覆盖 or 树形DP)

Strategic game Description Bob enjoys playing computer games, especially strategic games, but sometimes he cannot find the solution fast enough and then he is very sad. Now he has the following problem. He must defend a medieval city, the roads of wh

【uva 1471】Defense Lines(算法效率--使用数据结构)

题意:给一个长度为N(N≤200000)的序列,要删除一个连续子序列,使得剩下的序列中有一个长度最大的连续递增子序列,输出其长度. 解法:(参考自紫书)1.X 暴力枚举删除的区间 [l,r],O(n^2),再数需要O(n).总共O(n^3). 2.X 前者+O(n)预处理 f[i] 和 g[i] 表示前缀和后缀的长度最大的连续递增子序列长度.总共O(n^2). 3.√ 前者O(n)预处理+ 只枚举 r(部分枚举),快速找最优的 l.而最优的就是 Ai 尽量小而f[i]尽量大,就可以排除掉 Ai≤

IT英语4-计算机英语缩写术语

1.CPU 3DNow!(3D no waiting,无须等待的3D处理) AAM(AMD Analyst Meeting,AMD分析家会议) ABP(Advanced Branch Prediction,高级分支预测) ACG(Aggressive Clock Gating,主动时钟选择) AIS(Alternate Instruction Set,交替指令集) ALAT(advanced load table,高级载入表) ALU(Arithmetic Logic Unit,算术逻辑单元) 

没有银弹:软件工程的本质性与附属性工作

NO SILVER BULLET: ESSENCE AND ACCIDENTS OF SOFTWARE ENGINEERING It's adapted from berkeley . If you want to know more, you visit the orignal articlehere. if you want to understand this article more clear please  first read this chinese article here.

UVA 1292 十二 Strategic game

Strategic game Time Limit:3000MS     Memory Limit:0KB     64bit IO Format:%lld & %llu Submit Status Practice UVA 1292 Bob enjoys playing computer games, especially strategic games, but sometimes he cannot find the solution fast enough and then he is

UVA 1471 - Defense Lines(扫描+二分)

UVA 1471 - Defense Lines 题目链接 题意:给定一个序列,要求删去一个连续子序列后,得到的序列有一个最长的连续递增序列,输出最长连续递增序列长度 思路:先左右扫描一遍,把每个位置往左和往右的最大长度记录下来,然后在从左往右扫描一遍,开一个数组Min用来记录长度i的序列,最后一位的最小值,这个序列是满足单调性的,因为递增序列肯定是1,2,3,4...这样不断往上加的,如果遇到一个a[i]比较小的,就维护Min相应长度下的值,这样在这个单调递增的序列中,每次就可以二分找出最后一

UVA - 1471 Defense Lines 树状数组/二分

                              Defense Lines After the last war devastated your country, you - as the king of the land of Ardenia - decided it washigh time to improve the defense of your capital city. A part of your forti?cation is a line of magetower

uva 1471 Defense Lines

题意: 给一个长度为n(n <= 200000) 的序列,你删除一段连续的子序列,使得剩下的序列拼接起来,有一个最长的连续递增子序列 分析: 就是最长上升子序列的变形.需要加一个类似二分搜索就好. 代码: #include <iostream>#include <cstdio>#include <algorithm>#include <cstring>using namespace std;const int maxn=200005;const int

uva 1471 Defense Lines (降低复杂度)

题意: 给一个长度为n(n <= 200000) 的序列,你删除一段连续的子序列,使得剩下的序列拼接起来,有一个最长的连续递增子序列 思路: 设f[i] 和g[i] 分别表示 以i为开始 和 以i为结束 的最长连续递增序列长度 首先可以想到枚举i和j,然后计算max_len = f[i] + g[i]; 但是这种枚举方法的时间复杂度是O(n^2),这是在加上预处理f[i] 和g[i] 的前提下 所以需要想一个更加优化的方法,避免那么多枚举: 所以想到 只枚举f[i], 通过某种方法快速的找到合适