zoukankan      html  css  js  c++  java
  • 各种子序列问题

    最长严格上升子序列

    LIS问题,动归时间复杂度o(n2),可以用单调队列优化到o(nlogn)

    http://blog.csdn.net/dangwenliang/article/details/5728363

    #include<iostream>
    #include<cstdio>
    #include<algorithm>
    using namespace std;
    int n,dp[5005],orz[5005],ans = 0;
    int main(){
        cin>>n;
        for(int i = 1;i <= n;i++) scanf("%d",&orz[i]);
        for(int i = 1;i <= n;i++){
            dp[i] = 1;
            for(int j = 1;j < i;j++){
                if(orz[i] > orz[j])dp[i] = max(dp[i],dp[j]+1);
                ans = max(ans,dp[i]);
            }
        }
        cout<<ans;
        return 0;
    }
    #include <iostream>
    using namespace std;
    int find(int *a,int len,int n)//修改后的二分查找,若返回值为x,则a[x]>=n
    {
        int left=0,right=len,mid=(left+right)/2;
        while(left<=right)
        {
           if(n>a[mid]) left=mid+1;
           else if(n<a[mid]) right=mid-1;
           else return mid;
           mid=(left+right)/2;
        }
        return left;
    }
         
    int main(void)
    {
        int n,a[100],c[100],i,j,len;//新开一变量len,用来储存每次循环结束后c中已经求出值的元素的最大下标
        while(cin>>n)
        {
            for(i=0;i<n;i++)
                cin>>a[i];
            b[0]=1;
            c[0]=-1;
            c[1]=a[0];
            len=1;//此时只有c[1]求出来,最长递增子序列的长度为1.
            for(i=1;i<n;i++)
            {
                j=find(c,len,a[i]);
                c[j]=a[i];
                if(j>len)//要更新len,另外补充一点:由二分查找可知j只可能比len大1
                    len=j;//更新len
            }
            cout<<len<<endl;
        }
        return 0;
    }

    合唱队形

    #include<iostream>
    #include<cstdio>
    #include<string>
    #include<cstring>
    #include<algorithm>
    
    using namespace std;
    const int maxn = 200;
    int dp[maxn],dps[maxn],value[maxn],n;
    
    int main(){
        cin>>n;
        for(int i =1;i <= n;i++) cin>>value[i];
        dp[1] = dps[n] = 1;
        for(int i = 2;i <= n;i++){
            for(int j = 1;j < i;j++){
                if(dp[j] > dp[i] && value[i] > value[j]) dp[i] = dp[j];
            }
            dp[i]++;
            
        }
        for(int i = n-1;i >= 1;i--){
            for(int j = n;j > i;j--){
                if(dps[j] > dps[i] && value[i] > value[j]) dps[i] = dps[j];
            }
            dps[i]++;
            
        }
        int ans = 0;
        for(int i = 1;i <= n;i++) ans = max(ans,dp[i] + dps[i] - 1);
        cout<<n - ans;
        return 0;
    }
  • 相关阅读:
    Oracle 字符串转多行(REGEXP_SUBSTR)
    Word使用技巧总结
    VirtualBox配置安装入门(Linux连不上网络和设置共享文件夹)
    (vm/vb)虚拟机复制或者拷贝之后连不上网络怎么处理?
    Vmware共享文件夹安装设置方法(window与Linux使用共享文件夹)
    软删除和硬删除的处理方法
    banner小点点
    常用标签
    优雅批量删除redis匹配数据
    rabbitmq(三)- 交换机
  • 原文地址:https://www.cnblogs.com/hyfer/p/5811926.html
Copyright © 2011-2022 走看看