求最长上升子序列长度:

单纯的dp时间复杂度是O(n*n)的

dp[i] = max(dp[j]+1); (0=<j<=i-1 && a[i]>a[j])

用二分可以减少查找的时间:时间复杂度:O(n*log(n))

模板:

#define maxn 100010
int a[maxn], b[maxn]; // 二分在b[] 数组里找第一个比num 大的数的位置。
int search_(int num, int low, int high) {
int mid;
while(low <= high) {
mid = (low+high)/2;
if (num >= b[mid]) low = mid + 1;
else high = mid - 1;
}
return low;
} int LIS(int n) {
int i, len, pos;
b[1] = a[1];
len = 1;
for (i=2; i<=n; ++i) {
if (a[i] > b[len]) {// 如果a[i]比b[]中最大的数还大直接插入到最后。 //如果是非递减序列,改为 >= 即可。
len = len + 1;
b[len] = a[i];
}
else {
pos = search_(a[i], 1, len);
b[pos] = a[i];
}
}
return len;
}

Eg:题目链接:The All-purpose Zero

题意:给一个序列,序列里的0可以代替任何数,问这个序列里最长递增子序列的长度。0也可以代替负数。(如果不可以的话...)

思路:因为0可以代替任何数,所以ans一定是优先选择0的,然后把每个数减掉它前面的0的个数。为什么减0呢... 比如:1 2 0 3 优先选0,3-1=2,... ,这样就变成了1 2 2 ...求最长上升子序列的长度+0的个数。

#include <stdio.h>
#include <string.h>
#include <iostream>
using namespace std; #define maxn 100010
int a[maxn], b[maxn]; // 二分在b[] 数组里找第一个比num 大的数的位置。
int search_(int num, int low, int high) {
int mid;
while(low <= high) {
mid = (low+high)/2;
if (num >= b[mid]) low = mid + 1;
else high = mid - 1;
}
return low;
} int LIS(int n) {
int i, len, pos;
b[1] = a[1];
len = 1;
for (i=2; i<=n; ++i) {
if (a[i] > b[len]) {// 如果a[i]比b[]中最大的数还大直接插入到最后。 //如果是非递减序列,改为 >= 即可。
len = len + 1;
b[len] = a[i];
}
else {
pos = search_(a[i], 1, len);
b[pos] = a[i];
}
}
return len;
} int main() {
//freopen("in.cpp", "r", stdin);
int t;
scanf("%d", &t);
int cas = 0;
while(t--) {
int n;
scanf("%d", &n);
int zeroNum = 0, cnt = 0;
for (int i=0; i<n; ++i) {
int temp;
scanf("%d", &temp);
if (temp == 0) zeroNum++;
else {
temp -= zeroNum;
a[++cnt] = temp;
}
}
int ans = LIS(cnt) + zeroNum;
if (cnt == 0) ans -= 1;
printf("Case #%d: %d\n", ++cas, ans);
}
return 0;
}

HDU 5773 The All-purpose Zero 求LIS的更多相关文章

  1. hdu 1025LIS思路同1257 二分求LIS

    题目: Constructing Roads In JGShining's Kingdom Time Limit: 2000/1000 MS (Java/Others)    Memory Limit ...

  2. HDU 5773 The All-purpose Zero(O(nlgn)求LIS)

    http://acm.hdu.edu.cn/showproblem.php?pid=5773 题意: 求LIS,其中的0可以看做任何数. 思路: 因为0可以看做任何数,所以我们可以先不管0,先求一遍L ...

  3. HDU 5773:The All-purpose Zero(贪心+LIS)

    http://acm.hdu.edu.cn/showproblem.php?pid=5773 The All-purpose Zero Problem Description   ?? gets an ...

  4. HDU 5773 The All-purpose Zero 脑洞LIS

    给定一个序列,里面的0是可以任变的.问变化后最长的LIS的长度 首先,0全部选上是不亏的.这个不知道怎么说,YY一下吧. 最关键的就是解决2 0 0 3 这种问题了. 注意到这个序列的LIS应该是3 ...

  5. hdu 5773 The All-purpose Zero 最长上升子序列+树状数组

    题目链接:hdu 5773 The All-purpose Zero 官方题解:0可以转化成任意整数,包括负数,显然求LIS时尽量把0都放进去必定是正确的. 因此我们可以把0拿出来,对剩下的做O(nl ...

  6. hdu 1950 最长上升子序列(lis) nlogn算法【dp】

    这个博客说的已经很好了.http://blog.csdn.net/shuangde800/article/details/7474903 简单记录一下自己学的: 问题就是求一个数列最长上升子序列的长度 ...

  7. Codeforces 486E LIS of Sequence --树状数组求LIS

    题意: 一个序列可能有多个最长子序列,现在问每个元素是以下三个种类的哪一类: 1.不属于任何一个最长子序列 2.属于其中某些但不是全部最长子序列 3.属于全部最长子序列 解法: 我们先求出dp1[i] ...

  8. HDU 5773 The All-purpose Zero

    这题想了1个多小时想不出来...方法真是精妙... 官方题解:0可以转化成任意整数,包括负数,显然求LIS时尽量把0都放进去必定是正确的.因此我们可以把0拿出来,对剩下 的做O(nlogn)的LIS, ...

  9. hdu5256 二分求LIS+思维

    解题的思路很巧,为了让每个数之间都留出对应的上升空间,使a[i]=a[i]-i,然后再求LIS 另外二分求LIS是比较快的 #include<bits/stdc++.h> #define ...

  10. poj1631——树状数组求LIS

    题目:http://poj.org/problem?id=1631 求LIS即可,我使用了树状数组. 代码如下: #include<iostream> #include<cstdio ...

随机推荐

  1. LINQ之路 5:LINQ查询表达式

    书写LINQ查询时又两种语法可供选择:方法语法(Fluent Syntax)和查询表达式(Query Expression). LINQ方法语法的本质是通过扩展方法和Lambda表达式来创建查询.C# ...

  2. weblogic与axis2 jar包冲突

    1.org.springframework.web.util.NestedServletException: Handler processing failed; nested exception i ...

  3. Spring的自动扫描与管理

    通过在classpath自动扫描方式把组件纳入spring容器中管理 前面的例子我们都是使用XML的bean定义来配置组件.在一个稍大的项目中,通常会有上百个组件,如果这些这组件采用xml的bean定 ...

  4. NS3 日志(Logging)、命令行参数、Tracing系统概述(转载)

    NS-3日志子系统的提供了各种查看仿真结果的渠道: 一.使用Logging Module 1 [预备知识]日志级别及其对应的宏 NS-3 提供了若干个日志级别来满足不同的 Debug 需求,每一级的日 ...

  5. MongoDB 中遇到的一些错误

    1.在win平台上,使用ctrl+c关闭mongodb后,使用 mongod --dbpath=D:\mongodb\db --logpath=D:\mongodb\log.txt --port -- ...

  6. 这只是一篇用Markdown写的随记,就是熟悉熟悉MarkDown而已

    这几天的随想 今天是八月十一号了,来到公司实习已经第八天了,包块周末的话就是十二天了,我在这十二天里干了什么,转眼半个月就过去了 马上就要开学了,这个暑假干了些什么,单词单词也没背多少,之前七月回家有 ...

  7. poj1266Cover an Arc(三角形外接圆)

    链接 求出三角形的外接圆,通过圆心和半径可以知道这个圆的上下左右最远点,分别判断这个四个点跟弧的两端点A,B的关系,假如判断P点,弧内给出点为C,判断PC是否与AB相交即可判断出P是否在弧上. 精度问 ...

  8. Ubuntu系统下面软件安装更新命令

    在ubuntu服务器下安装包的时候,经常会用到sudo apt-get install 包名 或 sudo pip install 包名,那么两者有什么区别呢? 1.区别 pip用来安装来自PyPI( ...

  9. [js]事件综合 整理

    原文链接:http://www.cnblogs.com/xxcanghai/p/5205998.html 事件流:页面接收事件的顺序,IE提出了事件冒泡流,Netscape提出了事件捕获流. 事件冒泡 ...

  10. C#_DataTable导出Execl为自定义标题

    public bool ExportExcel(DataTable tb, string path, string tbName) { //excel 2003格式 string connString ...