NOIP200407合唱队形+最长上升子序列O(n^2)详解
合唱队形解题报告
2016-05-12 4:30——6:45
|
NOIP200407合唱队形 |
|
难度级别:A; 运行时间限制:1000ms; 运行空间限制:256000KB; 代码长度限制:2000000B |
|
试题描述 |
|
N位同学站成一排,音乐老师要请其中的(N-K)位同学出列,使得剩下的K位同学排成合唱队形。 |
|
输入 |
|
第一行是一个整数N(2<=N<=100),表示同学的总数。第一行有n个整数,用空格分隔,第i个整数Ti(130<=Ti<=230)是第i位同学的身高(厘米)。 |
|
输出 |
|
包括一行,这一行只包含一个整数,就是最少需要几位同学出列。 |
|
输入示例 |
|
8 |
|
输出示例 |
|
4 |
|
其他说明 |
|
数据范围:n<=100。 |
代码:
#include<iostream>
using namespace std;
int b[],c[],a[];
// 分别定义了三个数组:数组a(用来储存输入数据),数组b(用来存储从a[1]到a[n]的最大严格上升子序列长度),数组c(用来存储从a[n]到a[1]的最大严格下降子序列长度)
int main()
{
int n,ans=,i,j;
scanf("%d",&n);//输入
for(i=;i<=n;i++) scanf("%d",&a[i]);
b[]=;
for(i=;i<=n;i++)
//从a[2]开始求最大严格上升子序列长度
{
b[i]=;
for(j=;j<i;j++)
if(a[i]>a[j]) b[i]=max(b[i],b[j]+);
//如果a[i]>a[j],则可能从a[1]到a[i]的最大严格上升子序列长度又增加了1。
}
c[n]=;
//从a[n]开始求最大严格上升子序列长度
for(i=n-;i>=;i--)
{
c[i]=;
for(j=n;j>i;j--)
if(a[i]>a[j]) c[i]=max(c[i],c[j]+);
//如果a[i]<a[j],则可能从a[i]到a[n]的最大严格上升子序列长度又增加了1。
}
for(i=;i<=n;i++)
if(b[i]+c[i]>ans) ans=b[i]+c[i];//更新答案
printf("%d",n-ans+);//输出
}
《合唱队形》这道题其实就是《求最长下降/上升子序列》的翻版。但如果用循环直接搜固然很难办,而且不知道会用多长时间,所以,简单动态规划的思想很容易办到。
b[i]=1;
这句赋值语句固然很好理解,每一个元素,也可以视为一个符合题意的子序列,不论是最长上升、最长下降。所以从a[1]
到a[i]的符合题意的子序列必将有一个。比如有如下一组数。

b[1]是 1,原因如上。
那b[2]呢?如图,它显然比a[1]高,在执行如下语句时
for(j=1;j<i;j++) if(a[i]>a[j])
j小于i,也就是2,目前符合条件的只有a[1],a[1]又通过了判断语句,它确实小于a[i],执行下一条语句:
b[i]=max(b[i],b[j]+1);
b[2]显然原来是1,当它和b[1]+1比时,1当然比2小,所以,b[2]自然就是2了。由此,这个方法只需要一维数组就行了。、

O(nlogn)的方法,将下次介绍。这样的方法的时间复杂度为O(n^2)。

b[1]=1;
解决完了这个问题,这道题就非常简单了,先从下往上搜一遍最长上升子序列,代码如下:
for(i=2;i<=n;i++)
{
b[i]=1;
for(j=1;j<i;j++)
if(a[i]>a[j])
b[i]=max(b[i],b[j]+1);
}

再反着从上往下搜一下最长上升子序列:

这段代码一定就很好理解了:
for(i=1;i<=n;i++)
if(b[i]+c[i]>ans) ans=b[i]+c[i];
一直更新ans,要求出队人数最少,自然要让保留人数最多。
最后输出n-ans+1。
NOIP200407合唱队形+最长上升子序列O(n^2)详解的更多相关文章
- P1091 合唱队形 最长上升子序列
思路:最长上升子序列 正着做一遍 倒着做一遍 然后 取最大值 #include<bits/stdc++.h> using namespace std; const int maxn=105 ...
- 最长上升子序列O(nlogn)算法详解
最长上升子序列 时间限制: 10 Sec 内存限制:128 MB 题目描述 给定一个序列,初始为空.现在我们将1到N的数字插入到序列中,每次将一个数字插入到一个特定的位置.我们想知道此时最长上升子 ...
- rnqoj-28-合唱队形-最长上升子序列
想当年大一的时候,一个最长上升子序列的问题使得我的罚时上升了不少....当年还是图样啊 这道题目本质就是求最长上升子序列 #include<stdio.h> #include<str ...
- LeetCode 873. 最长的斐波那契子序列的长度 题目详解
题目详情 如果序列 X_1, X_2, ..., X_n 满足下列条件,就说它是 斐波那契式 的: n >= 3 对于所有 i + 2 <= n,都有 X_i + X_{i+1} = X_ ...
- LCS最长公共子序列(最优线性时间O(n))
这篇日志主要为了记录这几天的学习成果. 最长公共子序列根据要不要求子序列连续分两种情况. 只考虑两个串的情况,假设两个串长度均为n. 一,子序列不要求连续. (1)动态规划(O(n*n)) (转自:h ...
- 洛谷 [p1439] 最长公共子序列 (NlogN)
可以发现只有当两个序列中都没有重复元素时(1-n的排列)此种优化才是高效的,不然可能很不稳定. 求a[] 与b[]中的LCS 通过记录lis[i]表示a[i]在b[]中的位置,将LCS问题转化为最长上 ...
- 最长公共子序列 nlogn
先来个板子 #include<bits/stdc++.h> using namespace std; , M = 1e6+, mod = 1e9+, inf = 1e9+; typedef ...
- NOIP 2004 T3 合唱队形(DP、最长上升/下降子序列)
链接:https://ac.nowcoder.com/acm/contest/1082/C来源:牛客网 题目描述 N位同学站成一排,音乐老师要请其中的(N-K)位同学出列,使得剩下的K位同学排成合唱队 ...
- 九度OJ 1131 合唱队形 -- 动态规划(最长递增子序列)
题目地址:http://ac.jobdu.com/problem.php?pid=1131 题目描述: N位同学站成一排,音乐老师要请其中的(N-K)位同学出列,使得剩下的K位同学不交换位置就能排成合 ...
随机推荐
- Selenium2学习-031-WebUI自动化实战实例-029-JavaScript 在 Selenium 自动化中的应用实例之四(获取元素位置和大小)
通过 JS 或 JQuery 获取到元素后,通过 offsetLeft.offsetTop.offsetWidth.offsetHeight 即可获得元素的位置和大小,非常的简单,直接上源码了,敬请参 ...
- JavaScript:画廊案例
经常会在网上看到这样的操作:有几个按钮.可以控制器图片的上一张.下一张.那么现在就使用按钮的click单击事件来切换img的图片. 此时由于只是简单的演示,将所有的图片保存在images目录中.所有的 ...
- 图像分割之(二)Graph Cut(图割)
zouxy09@qq.com http://blog.csdn.net/zouxy09 上一文对主要的分割方法做了一个概述.那下面我们对其中几个比较感兴趣的算法做个学习.下面主要是Graph Cut, ...
- json解析转map
HashMap<String, Object> map = new HashMap<String, Object>(); JSONObject jsonObject = ...
- VMWare ESXi 5.5安装及配置
VMWare ESXi 5.5安装大概过程如下:制作虚拟化ESXi系统的USB启动盘,安装ESXi系统到USB,用USB启动ESXi系统.比较难理解,下面图解过程. 下载UNetbootin (下 ...
- [g2o]一个备忘
g2o使用的一个备忘 位姿已知,闭环的帧已知,进行图优化. #include "stdafx.h" #include <vector> #include "P ...
- Save ITCM
Debug String if below 64 BYTE it will in DRAM or it will in ITCM So to save ITCM , move it to ALLStr ...
- Java基础之在窗口中绘图——使用模型/视图体系结构在视图中绘图(Sketcher 1 drawing a 3D rectangle)
控制台程序. 在模型中表示数据视图的类用来显示草图并处理用户的交互操作,所以这种类把显示方法和草图控制器合并在一起.不专用于某个视图的通用GUI创建和操作在SketcherFrame类中处理. 模型对 ...
- Java基础之创建窗口——使窗口在屏幕居中(TryWindow2/TryWindow3)
控制台程序. 1.使用ToolKit对象在屏幕的中心显示窗口,将窗口的宽度和高度设置为屏幕的一半: import javax.swing.JFrame; import javax.swing.Swin ...
- Sql清理日志文件
场景: 我们导入MR数据时发现磁盘空间不够用了,导致的结果就是我们的程序很可能会抛出异常了,我们需要导入数据的时候进行日志瘦身. 问1:导入数据的时候,瘦身是否会造成数据库的异常? DBA提供解决方案 ...