• 序列变换(Lis变形)


    序列变换

    Time Limit: 2000/1000 MS (Java/Others)    Memory Limit: 32768/32768 K (Java/Others) Total Submission(s): 1200    Accepted Submission(s): 448

    Problem Description
    我们有一个数列A1,A2...An,你现在要求修改数量最少的元素,使得这个数列严格递增。其中无论是修改前还是修改后,每个元素都必须是整数。 请输出最少需要修改多少个元素。
     
    Input
    第一行输入一个T(1T10),表示有多少组数据
    每一组数据:
    第一行输入一个N(1N105),表示数列的长度
    第二行输入N个数A1,A2,...,An
    每一个数列中的元素都是正整数而且不超过106
     
    Output
    对于每组数据,先输出一行
    Case #i:
    然后输出最少需要修改多少个元素。
     
    Sample Input
    2 2 1 10 3 2 5 4
     
    Sample Output
    Case #1: 0 Case #2: 1
     
    Source

    题解:

    改变系列使成为单调递增子序列;那么只需要dp[i]-dp[j]>=i-j就好了;再加上单调递增子序列的求法;

    dp[i]-dp[j]>=i-j即为dp[i]-i>=dp[j]-j;

    代码:

    #include<iostream>
    #include<cstdio>
    #include<cstring>
    #include<cmath>
    #include<algorithm>
    #include<vector>
    using namespace std;
    const int MAXN = 1e5 + 100;
    int num[MAXN];
    int dp[MAXN];
    vector<int>vec;
    /*
    int main(){
        int T, N, kase = 0;
        scanf("%d", &T);
        while(T--){
            vec.clear();
            scanf("%d", &N);
            for(int i = 0; i < N; i++){
                scanf("%d", num + i);
                num[i] -= i;
                if(upper_bound(vec.begin(), vec.end(), num[i]) == vec.end()){
                    vec.push_back(num[i]);
                }
                else{
                    int p = upper_bound(vec.begin(), vec.end(), num[i]) - vec.begin();
                    vec[p] = num[i];
                }
            }
            printf("Case #%d:
    %d
    ", ++kase, N - vec.size());
        }
        return 0;
    }
    */
    
    int main(){
        int T, N, kase = 0;
        scanf("%d", &T);
        while(T--){
            scanf("%d", &N);
            memset(dp, 0, sizeof(dp));
            int ans = 0;
            for(int i = 0; i < N; i++){
                scanf("%d", num + i);
                for(int j = 0; j < i; j++){
                    if(num[i] - num[j] >= i - j){
                        dp[i] = dp[j] + 1;
                        ans = max(ans, dp[i]);
                    }
                }
            }
            printf("Case #%d:
    %d
    ", ++kase, N - ans - 1);
        }
        return 0;
    }
  • 相关阅读:
    移动端工作心得
    小程序初探
    你可能会用到的"奇技赢巧"
    一个知乎日报pwa
    Progressive Web Applications
    Java中的基本数据类型以及装箱、拆箱
    用sql获得指定记录的空段数目和字段名称--实在想不通,这种场景应用在哪
    putIfAbsent,一个字段为空的话,将该字段设置为指定值
    PO、VO、BO、POJO、DAO、DTO都是什么对象
    Java中字符串连接符(+)和append的区别
  • 原文地址:https://www.cnblogs.com/handsomecui/p/5373794.html
Copyright © 2020-2023  润新知