zoukankan      html  css  js  c++  java
  • NYOJ 214 单调递增子序列(二)

    单调递增子序列(二)

    时间限制:1000 ms  |  内存限制:65535 KB
    难度:4
     
    描述

    给定一整型数列{a1,a2...,an}(0<n<=100000),找出单调递增最长子序列,并求出其长度。

    如:1 9 10 5 11 2 13的最长单调递增子序列是1 9 10 11 13,长度为5。

     
    输入
    有多组测试数据(<=7)
    每组测试数据的第一行是一个整数n表示序列中共有n个整数,随后的下一行里有n个整数,表示数列中的所有元素.每个整形数中间用空格间隔开(0<n<=100000)。
    数据以EOF结束 。
    输入数据保证合法(全为int型整数)!
    输出
    对于每组测试数据输出整形数列的最长递增子序列的长度,每个输出占一行。
    样例输入
    7
    1 9 10 5 11 2 13
    2
    2 -1
    样例输出
    5
    1

    解题:数据量大啊,o(n^2)方法不奏效啊!只有o(nlogn)算法了

    先附上TLE代码吧

     1 #include <iostream>
     2 #include <cstdio>
     3 #include <cstring>
     4 #include <cstdlib>
     5 #include <vector>
     6 #include <climits>
     7 #include <algorithm>
     8 #include <cmath>
     9 #define LL long long
    10 using namespace std;
    11 int d[100010],dp[100010];
    12 int main(){
    13     int n,i,j,ans;
    14     while(~scanf("%d",&n)){
    15         for(i = 1; i <= n; i++){
    16             scanf("%d",d+i);
    17             dp[i] = 1;
    18         }
    19         ans = 1;
    20         for(i = 2; i <= n; i++){
    21             for(j = i-1; j; j--){
    22                 if(d[j] < d[i] && dp[i] < dp[j]+1) dp[i] = dp[j]+1;
    23             }
    24             if(dp[i] > ans) ans = dp[i];
    25         }
    26         printf("%d
    ",ans);
    27     }
    28     return 0;
    29 }
    View Code
    好吧,上 AC 代码,O(nlogn)算法,精妙之处在于折半查找,速度很快的。噢最后那个top?top:1可以去掉的,秀逗了!损失4ms。

     1 #include <iostream>
     2 #include <cstdio>
     3 #include <cstring>
     4 #include <cstdlib>
     5 #include <vector>
     6 #include <climits>
     7 #include <algorithm>
     8 #include <cmath>
     9 #define LL long long
    10 using namespace std;
    11 int stk[100010],top;
    12 void bsearch(int lt,int rt,int val) {
    13     int mid;
    14     while(lt <= rt) {
    15         mid = (lt+rt)>>1;
    16         if(val < stk[mid]) rt = mid-1;
    17         else lt = mid+1;
    18     }
    19     stk[lt] = val;
    20 }
    21 int main() {
    22     int n,i,temp;
    23     while(~scanf("%d",&n)) {
    24         top = 0;
    25         for(i = 1; i <= n; i++) {
    26             scanf("%d",&temp);
    27             if(!top || stk[top-1] < temp)
    28                 stk[top++] = temp;
    29             else bsearch(0,top-1,temp);
    30         }
    31         printf("%d
    ",top?top:1);
    32     }
    33     return 0;
    34 }
    View Code
     
  • 相关阅读:
    oracle安装过程中遇到的问题
    HttpContext.Current 的缺陷
    oracle 复杂语句
    .net 中 ref out params的区别
    查看修改mysql编码方式[转载]
    Oracle 中的dual是什么东西
    KindEditor问题汇总【不定时更新】
    java中import、package作用和用法
    [笔记]: 哈弗曼树(最优二叉树) 标签: 二叉树 2017-05-17 16:38 34人阅读 评论(0) 收
    [noip 2004普及组] FBI树 标签: 二叉树递归 2017-05-17 14:29 40人阅读 评论(0)
  • 原文地址:https://www.cnblogs.com/crackpotisback/p/3847443.html
Copyright © 2011-2022 走看看