zoukankan      html  css  js  c++  java
  • hdu 4719 动态规划

    思路:dp[i]表示到第i个点为结尾能获得的最大值,那么dp[i]=h[i]*h[i]+dp[i-x]-h[i-x];(i-l<=x<=i);那么我们可以转换下,以dp[i]-h[i]为新的权值,动态方程就变成了dp[i]=dp[i-x]+h[i]*h[i](i-l<=x<=i);只要找到最大的dp[i-x]就可以了。可以用线段树维护。

    #include<set>
    #include<cmath>
    #include<queue>
    #include<cstdio>
    #include<vector>
    #include<string>
    #include<cstdlib>
    #include<cstring>
    #include<iostream>
    #include<algorithm>
    #define pb push_back
    #define mp make_pair
    #define Maxn 100010
    #define Maxm 80002
    #define LL __int64
    #define Abs(x) ((x)>0?(x):(-x))
    #define lson(x) (x<<1)
    #define rson(x) (x<<1|1)
    #define inf 10000000
    #define lowbit(x) (x&(-x))
    #define clr(x,y) memset(x,y,sizeof(x))
    #define Mod 1000000007
    using namespace std;
    int h[Maxn],sorted[Maxn];
    int r[Maxn];
    LL dp[Maxn],ans;
    struct Tree{
        int l,r;
        LL Max;
        int mid(){
            return (l+r)>>1;
        }
    }tree[Maxn*3];
    int cmp(int a,int b)
    {
        if(sorted[a]==sorted[b])
            return b<a;
        return sorted[a]<sorted[b];
    }
    void BuildTree(int l,int r,int po)
    {
        tree[po].l=l,tree[po].r=r,tree[po].Max=-1;
        if(l==r) return ;
        int mid=tree[po].mid();
        BuildTree(l,mid,lson(po));
        BuildTree(mid+1,r,rson(po));
    }
    void update(int i,LL val,int po)
    {
        if(tree[po].l==tree[po].r){
            tree[po].Max=val;
            return ;
        }
        int mid=tree[po].mid();
        if(i<=mid)
            update(i,val,lson(po));
        else
            update(i,val,rson(po));
        tree[po].Max=max(tree[lson(po)].Max,tree[rson(po)].Max);
    }
    void query(int i,int po)
    {
        if(i==0)
            return ;
        if(tree[po].r==i){
            ans=max(ans,tree[po].Max);
            return ;
        }
        int mid=tree[po].mid();
        if(i<=mid)
            query(i,lson(po));
        else{
            query(mid,lson(po));
            query(i,rson(po));
        }
    }
    int main()
    {
        int t,i,j,Case=0,n,l;
        scanf("%d",&t);
        while(t--){
            clr(dp,-1);
            scanf("%d%d",&n,&l);
            for(i=1;i<=n;i++){
                scanf("%d",h+i);
                sorted[i]=h[i];
            }
            for(i=1;i<=n;i++) r[i]=i;
            sort(r+1,r+n+1,cmp);
            int pos[Maxn];
            for(i=1;i<=n;i++) pos[r[i]]=i;
            BuildTree(1,n,1);
            for(i=1;i<=n;i++){
                ans=-1;
                query(pos[i]-1,1);
                if(i<=l)
                    dp[i]=(LL)h[i]*h[i];
                if(ans>=0)
                dp[i]=max(dp[i],(LL)h[i]*h[i]+ans);
                update(pos[i],dp[i]-(LL)h[i],1);
                if(i-l>0)
                    update(pos[i-l],-1,1);
            }
            printf("Case #%d: ",++Case);
            if(dp[n]<0)
                printf("No solution
    ");
            else
                printf("%I64d
    ",dp[n]);
        }
        return 0;
    }
  • 相关阅读:
    第3课 线性分类器损失函数与最优化
    李飞飞机器视觉课程笔记:第2课 K最近邻与线性分类器
    周志华《机器学习》第二章学习笔记
    通过anaconda安装tensorflow
    周志华《机器学习》第一章学习笔记 奥卡姆剃刀原理、没有免费的午餐定理(NFL)、回归模型
    DPM目标检测模型
    损失函数的理解
    mini-batch的理解
    前向传播、后向传播
    SVM(支持向量机)的理解
  • 原文地址:https://www.cnblogs.com/wangfang20/p/3316680.html
Copyright © 2011-2022 走看看